[{"data":1,"prerenderedAt":1582},["ShallowReactive",2],{"navigation":3,"/operations/deployment":145,"/operations/deployment-surround":1577},[4,28,49,88,101,127],{"title":5,"path":6,"stem":7,"children":8,"icon":27},"Getting Started","/getting-started","1.getting-started/1.index",[9,11,15,19,23],{"title":10,"path":6,"stem":7},"Introduction",{"title":12,"path":13,"stem":14},"Working with Agents","/getting-started/working-with-agents","1.getting-started/2.working-with-agents",{"title":16,"path":17,"stem":18},"Setup a Service Provider","/getting-started/setup-service-provider","1.getting-started/3.setup-service-provider",{"title":20,"path":21,"stem":22},"Setup an Identity Provider","/getting-started/setup-identity-provider","1.getting-started/4.setup-identity-provider",{"title":24,"path":25,"stem":26},"Developers","/getting-started/developers","1.getting-started/5.developers",false,{"title":29,"icon":27,"path":30,"stem":31,"children":32,"page":27},"Guides","/guides","2.guides",[33,37,41,45],{"title":34,"path":35,"stem":36},"How It Works","/guides/how-it-works","2.guides/1.how-it-works",{"title":38,"path":39,"stem":40},"Capabilities Guide","/guides/capabilities-guide","2.guides/2.capabilities-guide",{"title":42,"path":43,"stem":44},"End-to-End Tutorial","/guides/end-to-end-tutorial","2.guides/3.end-to-end-tutorial",{"title":46,"path":47,"stem":48},"Delegation Guide","/guides/delegation-guide","2.guides/4.delegation-guide",{"title":50,"path":51,"stem":52,"children":53,"icon":27},"Ecosystem","/ecosystem","3.ecosystem/1.index",[54,56,60,64,68,72,76,80,84],{"title":55,"path":51,"stem":52},"Overview",{"title":57,"path":58,"stem":59},"grapes CLI","/ecosystem/grapes","3.ecosystem/2.grapes",{"title":61,"path":62,"stem":63},"shapes CLI","/ecosystem/shapes","3.ecosystem/3.shapes",{"title":65,"path":66,"stem":67},"escapes","/ecosystem/escapes","3.ecosystem/4.escapes",{"title":69,"path":70,"stem":71},"OpenApe Proxy","/ecosystem/proxy","3.ecosystem/5.proxy",{"title":73,"path":74,"stem":75},"OpenApe Browser","/ecosystem/browser","3.ecosystem/6.browser",{"title":77,"path":78,"stem":79},"OpenApe Auth","/ecosystem/auth","3.ecosystem/7.auth",{"title":81,"path":82,"stem":83},"OpenApe Grants","/ecosystem/grants","3.ecosystem/8.grants",{"title":85,"path":86,"stem":87},"nuxt-auth-sp","/ecosystem/nuxt-auth-sp","3.ecosystem/9.nuxt-auth-sp",{"title":89,"icon":27,"path":90,"stem":91,"children":92,"page":27},"Security","/security","4.security",[93,97],{"title":94,"path":95,"stem":96},"Compliance","/security/compliance","4.security/1.compliance",{"title":98,"path":99,"stem":100},"Threat Model","/security/threat-model","4.security/2.threat-model",{"title":102,"path":103,"stem":104,"children":105,"icon":27},"Reference","/reference","5.reference/1.index",[106,107,111,115,119,123],{"title":102,"path":103,"stem":104},{"title":108,"path":109,"stem":110},"IdP Configuration","/reference/idp-configuration","5.reference/2.idp-configuration",{"title":112,"path":113,"stem":114},"SP Configuration","/reference/sp-configuration","5.reference/3.sp-configuration",{"title":116,"path":117,"stem":118},"API Endpoints","/reference/api-endpoints","5.reference/4.api-endpoints",{"title":120,"path":121,"stem":122},"escapes Config","/reference/escapes-config","5.reference/5.escapes-config",{"title":124,"path":125,"stem":126},"Proxy Config","/reference/proxy-config","5.reference/6.proxy-config",{"title":128,"path":129,"stem":130,"children":131,"icon":27},"Operations","/operations","6.operations/1.index",[132,133,137,141],{"title":128,"path":129,"stem":130},{"title":134,"path":135,"stem":136},"Deployment","/operations/deployment","6.operations/2.deployment",{"title":138,"path":139,"stem":140},"Troubleshooting","/operations/troubleshooting","6.operations/3.troubleshooting",{"title":142,"path":143,"stem":144},"Monitoring","/operations/monitoring","6.operations/4.monitoring",{"id":146,"title":134,"body":147,"description":1571,"extension":1572,"links":1573,"meta":1574,"navigation":760,"path":135,"seo":1575,"stem":136,"__hash__":1576},"docs/6.operations/2.deployment.md",{"type":148,"value":149,"toc":1546},"minimark",[150,154,159,163,168,185,196,209,525,532,544,550,557,583,587,594,600,610,711,715,719,791,795,963,967,971,974,979,984,1013,1017,1041,1058,1062,1065,1217,1224,1337,1341,1344,1348,1354,1357,1420,1424,1427,1471,1475,1496,1500,1518,1521,1542],[151,152,134],"h1",{"id":153},"deployment",[155,156,158],"h2",{"id":157},"vercel-recommended","Vercel (Recommended)",[160,161,162],"p",{},"OpenApe is built on Nuxt/Nitro and works out of the box on Vercel.",[164,165,167],"h3",{"id":166},"idp-deployment","IdP Deployment",[169,170,171,179],"ol",{},[172,173,174,178],"li",{},[175,176,177],"strong",{},"Push to GitHub"," and link the repository in Vercel Dashboard",[172,180,181,184],{},[175,182,183],{},"Set environment variables"," in Vercel:",[186,187,192],"pre",{"className":188,"code":190,"language":191},[189],"language-text","NUXT_OPENAPE_IDP_RP_NAME=My Organization\nNUXT_OPENAPE_IDP_RP_ID=id.example.com\nNUXT_OPENAPE_IDP_RP_ORIGIN=https://id.example.com\nNUXT_OPENAPE_IDP_SESSION_SECRET=\u003Crandom-32+-chars>\nNUXT_OPENAPE_IDP_MANAGEMENT_TOKEN=\u003Crandom-64-chars>\nNUXT_OPENAPE_IDP_ADMIN_EMAILS=admin@example.com\n","text",[193,194,190],"code",{"__ignoreMap":195},"",[169,197,199],{"start":198},3,[172,200,201,204,205,208],{},[175,202,203],{},"Configure persistent storage"," in ",[193,206,207],{},"nuxt.config.ts",":",[186,210,214],{"className":211,"code":212,"language":213,"meta":195,"style":195},"language-typescript shiki shiki-themes material-theme-lighter material-theme material-theme-palenight","export default defineNuxtConfig({\n  modules: ['@openape/nuxt-auth-idp'],\n  nitro: {\n    storage: {\n      'openape-idp': {\n        driver: 's3',\n        bucket: 'my-openape-data',\n        region: 'eu-central-1',\n        accessKeyId: process.env.S3_ACCESS_KEY,\n        secretAccessKey: process.env.S3_SECRET_KEY\n      },\n      'openape-grants': {\n        driver: 's3',\n        bucket: 'my-openape-data',\n        region: 'eu-central-1',\n        accessKeyId: process.env.S3_ACCESS_KEY,\n        secretAccessKey: process.env.S3_SECRET_KEY\n      }\n    }\n  }\n})\n","typescript",[193,215,216,240,267,277,287,302,320,337,354,378,397,403,417,432,447,462,481,498,504,510,516],{"__ignoreMap":195},[217,218,221,225,228,232,236],"span",{"class":219,"line":220},"line",1,[217,222,224],{"class":223},"s7zQu","export",[217,226,227],{"class":223}," default",[217,229,231],{"class":230},"s2Zo4"," defineNuxtConfig",[217,233,235],{"class":234},"sTEyZ","(",[217,237,239],{"class":238},"sMK4o","{\n",[217,241,243,247,249,252,255,259,261,264],{"class":219,"line":242},2,[217,244,246],{"class":245},"swJcz","  modules",[217,248,208],{"class":238},[217,250,251],{"class":234}," [",[217,253,254],{"class":238},"'",[217,256,258],{"class":257},"sfazB","@openape/nuxt-auth-idp",[217,260,254],{"class":238},[217,262,263],{"class":234},"]",[217,265,266],{"class":238},",\n",[217,268,269,272,274],{"class":219,"line":198},[217,270,271],{"class":245},"  nitro",[217,273,208],{"class":238},[217,275,276],{"class":238}," {\n",[217,278,280,283,285],{"class":219,"line":279},4,[217,281,282],{"class":245},"    storage",[217,284,208],{"class":238},[217,286,276],{"class":238},[217,288,290,293,296,298,300],{"class":219,"line":289},5,[217,291,292],{"class":238},"      '",[217,294,295],{"class":245},"openape-idp",[217,297,254],{"class":238},[217,299,208],{"class":238},[217,301,276],{"class":238},[217,303,305,308,310,313,316,318],{"class":219,"line":304},6,[217,306,307],{"class":245},"        driver",[217,309,208],{"class":238},[217,311,312],{"class":238}," '",[217,314,315],{"class":257},"s3",[217,317,254],{"class":238},[217,319,266],{"class":238},[217,321,323,326,328,330,333,335],{"class":219,"line":322},7,[217,324,325],{"class":245},"        bucket",[217,327,208],{"class":238},[217,329,312],{"class":238},[217,331,332],{"class":257},"my-openape-data",[217,334,254],{"class":238},[217,336,266],{"class":238},[217,338,340,343,345,347,350,352],{"class":219,"line":339},8,[217,341,342],{"class":245},"        region",[217,344,208],{"class":238},[217,346,312],{"class":238},[217,348,349],{"class":257},"eu-central-1",[217,351,254],{"class":238},[217,353,266],{"class":238},[217,355,357,360,362,365,368,371,373,376],{"class":219,"line":356},9,[217,358,359],{"class":245},"        accessKeyId",[217,361,208],{"class":238},[217,363,364],{"class":234}," process",[217,366,367],{"class":238},".",[217,369,370],{"class":234},"env",[217,372,367],{"class":238},[217,374,375],{"class":234},"S3_ACCESS_KEY",[217,377,266],{"class":238},[217,379,381,384,386,388,390,392,394],{"class":219,"line":380},10,[217,382,383],{"class":245},"        secretAccessKey",[217,385,208],{"class":238},[217,387,364],{"class":234},[217,389,367],{"class":238},[217,391,370],{"class":234},[217,393,367],{"class":238},[217,395,396],{"class":234},"S3_SECRET_KEY\n",[217,398,400],{"class":219,"line":399},11,[217,401,402],{"class":238},"      },\n",[217,404,406,408,411,413,415],{"class":219,"line":405},12,[217,407,292],{"class":238},[217,409,410],{"class":245},"openape-grants",[217,412,254],{"class":238},[217,414,208],{"class":238},[217,416,276],{"class":238},[217,418,420,422,424,426,428,430],{"class":219,"line":419},13,[217,421,307],{"class":245},[217,423,208],{"class":238},[217,425,312],{"class":238},[217,427,315],{"class":257},[217,429,254],{"class":238},[217,431,266],{"class":238},[217,433,435,437,439,441,443,445],{"class":219,"line":434},14,[217,436,325],{"class":245},[217,438,208],{"class":238},[217,440,312],{"class":238},[217,442,332],{"class":257},[217,444,254],{"class":238},[217,446,266],{"class":238},[217,448,450,452,454,456,458,460],{"class":219,"line":449},15,[217,451,342],{"class":245},[217,453,208],{"class":238},[217,455,312],{"class":238},[217,457,349],{"class":257},[217,459,254],{"class":238},[217,461,266],{"class":238},[217,463,465,467,469,471,473,475,477,479],{"class":219,"line":464},16,[217,466,359],{"class":245},[217,468,208],{"class":238},[217,470,364],{"class":234},[217,472,367],{"class":238},[217,474,370],{"class":234},[217,476,367],{"class":238},[217,478,375],{"class":234},[217,480,266],{"class":238},[217,482,484,486,488,490,492,494,496],{"class":219,"line":483},17,[217,485,383],{"class":245},[217,487,208],{"class":238},[217,489,364],{"class":234},[217,491,367],{"class":238},[217,493,370],{"class":234},[217,495,367],{"class":238},[217,497,396],{"class":234},[217,499,501],{"class":219,"line":500},18,[217,502,503],{"class":238},"      }\n",[217,505,507],{"class":219,"line":506},19,[217,508,509],{"class":238},"    }\n",[217,511,513],{"class":219,"line":512},20,[217,514,515],{"class":238},"  }\n",[217,517,519,522],{"class":219,"line":518},21,[217,520,521],{"class":238},"}",[217,523,524],{"class":234},")\n",[526,527,529],"callout",{"type":528},"warning",[160,530,531],{},"The default storage driver is in-memory — data is lost on every deployment. Always configure S3 or another persistent driver for production.",[169,533,534],{"start":279},[172,535,536,539,540,543],{},[175,537,538],{},"Configure DNS"," — add a ",[193,541,542],{},"_ddisa"," TXT record for your domain:",[186,545,548],{"className":546,"code":547,"language":191},[189],"_ddisa.example.com  TXT  \"v=ddisa1 idp=https://id.example.com; mode=open\"\n",[193,549,547],{"__ignoreMap":195},[169,551,552],{"start":289},[172,553,554],{},[175,555,556],{},"Deploy:",[186,558,562],{"className":559,"code":560,"language":561,"meta":195,"style":195},"language-bash shiki shiki-themes material-theme-lighter material-theme material-theme-palenight","git push origin main  # Vercel deploys automatically\n","bash",[193,563,564],{"__ignoreMap":195},[217,565,566,570,573,576,579],{"class":219,"line":220},[217,567,569],{"class":568},"sBMFI","git",[217,571,572],{"class":257}," push",[217,574,575],{"class":257}," origin",[217,577,578],{"class":257}," main",[217,580,582],{"class":581},"sHwdD","  # Vercel deploys automatically\n",[164,584,586],{"id":585},"sp-deployment","SP Deployment",[169,588,589],{},[172,590,591],{},[175,592,593],{},"Set environment variables:",[186,595,598],{"className":596,"code":597,"language":191},[189],"NUXT_OPENAPE_SP_CLIENT_ID=app.example.com\nNUXT_OPENAPE_SP_SESSION_SECRET=\u003Crandom-32+-chars>\nNUXT_OPENAPE_SP_FALLBACK_IDP_URL=https://id.example.com\n",[193,599,597],{"__ignoreMap":195},[169,601,602],{"start":242},[172,603,604,607,608,208],{},[175,605,606],{},"Configure Nitro"," for Vercel in ",[193,609,207],{},[186,611,613],{"className":211,"code":612,"language":213,"meta":195,"style":195},"export default defineNuxtConfig({\n  modules: ['@openape/nuxt-auth-sp'],\n  nitro: {\n    preset: 'vercel',\n    externals: {\n      inline: ['@openape/nuxt-auth-sp']\n    }\n  }\n})\n",[193,614,615,627,646,654,670,679,697,701,705],{"__ignoreMap":195},[217,616,617,619,621,623,625],{"class":219,"line":220},[217,618,224],{"class":223},[217,620,227],{"class":223},[217,622,231],{"class":230},[217,624,235],{"class":234},[217,626,239],{"class":238},[217,628,629,631,633,635,637,640,642,644],{"class":219,"line":242},[217,630,246],{"class":245},[217,632,208],{"class":238},[217,634,251],{"class":234},[217,636,254],{"class":238},[217,638,639],{"class":257},"@openape/nuxt-auth-sp",[217,641,254],{"class":238},[217,643,263],{"class":234},[217,645,266],{"class":238},[217,647,648,650,652],{"class":219,"line":198},[217,649,271],{"class":245},[217,651,208],{"class":238},[217,653,276],{"class":238},[217,655,656,659,661,663,666,668],{"class":219,"line":279},[217,657,658],{"class":245},"    preset",[217,660,208],{"class":238},[217,662,312],{"class":238},[217,664,665],{"class":257},"vercel",[217,667,254],{"class":238},[217,669,266],{"class":238},[217,671,672,675,677],{"class":219,"line":289},[217,673,674],{"class":245},"    externals",[217,676,208],{"class":238},[217,678,276],{"class":238},[217,680,681,684,686,688,690,692,694],{"class":219,"line":304},[217,682,683],{"class":245},"      inline",[217,685,208],{"class":238},[217,687,251],{"class":234},[217,689,254],{"class":238},[217,691,639],{"class":257},[217,693,254],{"class":238},[217,695,696],{"class":234},"]\n",[217,698,699],{"class":219,"line":322},[217,700,509],{"class":238},[217,702,703],{"class":219,"line":339},[217,704,515],{"class":238},[217,706,707,709],{"class":219,"line":356},[217,708,521],{"class":238},[217,710,524],{"class":234},[155,712,714],{"id":713},"docker","Docker",[164,716,718],{"id":717},"idp-dockerfile","IdP Dockerfile",[186,720,724],{"className":721,"code":722,"language":723,"meta":195,"style":195},"language-dockerfile shiki shiki-themes material-theme-lighter material-theme material-theme-palenight","FROM node:22-slim AS builder\nWORKDIR /app\nCOPY package*.json ./\nRUN npm ci\nCOPY . .\nRUN npm run build\n\nFROM node:22-slim\nWORKDIR /app\nCOPY --from=builder /app/.output .output\nENV NODE_ENV=production\nEXPOSE 3000\nCMD [\"node\", \".output/server/index.mjs\"]\n","dockerfile",[193,725,726,731,736,741,746,751,756,762,767,771,776,781,786],{"__ignoreMap":195},[217,727,728],{"class":219,"line":220},[217,729,730],{},"FROM node:22-slim AS builder\n",[217,732,733],{"class":219,"line":242},[217,734,735],{},"WORKDIR /app\n",[217,737,738],{"class":219,"line":198},[217,739,740],{},"COPY package*.json ./\n",[217,742,743],{"class":219,"line":279},[217,744,745],{},"RUN npm ci\n",[217,747,748],{"class":219,"line":289},[217,749,750],{},"COPY . .\n",[217,752,753],{"class":219,"line":304},[217,754,755],{},"RUN npm run build\n",[217,757,758],{"class":219,"line":322},[217,759,761],{"emptyLinePlaceholder":760},true,"\n",[217,763,764],{"class":219,"line":339},[217,765,766],{},"FROM node:22-slim\n",[217,768,769],{"class":219,"line":356},[217,770,735],{},[217,772,773],{"class":219,"line":380},[217,774,775],{},"COPY --from=builder /app/.output .output\n",[217,777,778],{"class":219,"line":399},[217,779,780],{},"ENV NODE_ENV=production\n",[217,782,783],{"class":219,"line":405},[217,784,785],{},"EXPOSE 3000\n",[217,787,788],{"class":219,"line":419},[217,789,790],{},"CMD [\"node\", \".output/server/index.mjs\"]\n",[164,792,794],{"id":793},"docker-compose","Docker Compose",[186,796,800],{"className":797,"code":798,"language":799,"meta":195,"style":195},"language-yaml shiki shiki-themes material-theme-lighter material-theme material-theme-palenight","services:\n  idp:\n    build: ./idp\n    ports:\n      - \"3000:3000\"\n    environment:\n      NUXT_OPENAPE_IDP_RP_NAME: \"My Organization\"\n      NUXT_OPENAPE_IDP_RP_ID: \"id.example.com\"\n      NUXT_OPENAPE_IDP_RP_ORIGIN: \"https://id.example.com\"\n      NUXT_OPENAPE_IDP_SESSION_SECRET: \"${SESSION_SECRET}\"\n      NUXT_OPENAPE_IDP_MANAGEMENT_TOKEN: \"${MANAGEMENT_TOKEN}\"\n      S3_ACCESS_KEY: \"${S3_ACCESS_KEY}\"\n      S3_SECRET_KEY: \"${S3_SECRET_KEY}\"\n    restart: unless-stopped\n","yaml",[193,801,802,810,817,827,834,848,855,869,883,897,911,925,939,953],{"__ignoreMap":195},[217,803,804,807],{"class":219,"line":220},[217,805,806],{"class":245},"services",[217,808,809],{"class":238},":\n",[217,811,812,815],{"class":219,"line":242},[217,813,814],{"class":245},"  idp",[217,816,809],{"class":238},[217,818,819,822,824],{"class":219,"line":198},[217,820,821],{"class":245},"    build",[217,823,208],{"class":238},[217,825,826],{"class":257}," ./idp\n",[217,828,829,832],{"class":219,"line":279},[217,830,831],{"class":245},"    ports",[217,833,809],{"class":238},[217,835,836,839,842,845],{"class":219,"line":289},[217,837,838],{"class":238},"      -",[217,840,841],{"class":238}," \"",[217,843,844],{"class":257},"3000:3000",[217,846,847],{"class":238},"\"\n",[217,849,850,853],{"class":219,"line":304},[217,851,852],{"class":245},"    environment",[217,854,809],{"class":238},[217,856,857,860,862,864,867],{"class":219,"line":322},[217,858,859],{"class":245},"      NUXT_OPENAPE_IDP_RP_NAME",[217,861,208],{"class":238},[217,863,841],{"class":238},[217,865,866],{"class":257},"My Organization",[217,868,847],{"class":238},[217,870,871,874,876,878,881],{"class":219,"line":339},[217,872,873],{"class":245},"      NUXT_OPENAPE_IDP_RP_ID",[217,875,208],{"class":238},[217,877,841],{"class":238},[217,879,880],{"class":257},"id.example.com",[217,882,847],{"class":238},[217,884,885,888,890,892,895],{"class":219,"line":356},[217,886,887],{"class":245},"      NUXT_OPENAPE_IDP_RP_ORIGIN",[217,889,208],{"class":238},[217,891,841],{"class":238},[217,893,894],{"class":257},"https://id.example.com",[217,896,847],{"class":238},[217,898,899,902,904,906,909],{"class":219,"line":380},[217,900,901],{"class":245},"      NUXT_OPENAPE_IDP_SESSION_SECRET",[217,903,208],{"class":238},[217,905,841],{"class":238},[217,907,908],{"class":257},"${SESSION_SECRET}",[217,910,847],{"class":238},[217,912,913,916,918,920,923],{"class":219,"line":399},[217,914,915],{"class":245},"      NUXT_OPENAPE_IDP_MANAGEMENT_TOKEN",[217,917,208],{"class":238},[217,919,841],{"class":238},[217,921,922],{"class":257},"${MANAGEMENT_TOKEN}",[217,924,847],{"class":238},[217,926,927,930,932,934,937],{"class":219,"line":405},[217,928,929],{"class":245},"      S3_ACCESS_KEY",[217,931,208],{"class":238},[217,933,841],{"class":238},[217,935,936],{"class":257},"${S3_ACCESS_KEY}",[217,938,847],{"class":238},[217,940,941,944,946,948,951],{"class":219,"line":419},[217,942,943],{"class":245},"      S3_SECRET_KEY",[217,945,208],{"class":238},[217,947,841],{"class":238},[217,949,950],{"class":257},"${S3_SECRET_KEY}",[217,952,847],{"class":238},[217,954,955,958,960],{"class":219,"line":434},[217,956,957],{"class":245},"    restart",[217,959,208],{"class":238},[217,961,962],{"class":257}," unless-stopped\n",[155,964,966],{"id":965},"dns-setup","DNS Setup",[164,968,970],{"id":969},"ddisa-txt-record","DDISA TXT Record",[160,972,973],{},"For IdP discovery, add a TXT record to your domain:",[186,975,977],{"className":976,"code":547,"language":191},[189],[193,978,547],{"__ignoreMap":195},[160,980,981],{},[175,982,983],{},"Fields:",[985,986,987,993,999],"ul",{},[172,988,989,992],{},[193,990,991],{},"v=ddisa1"," — protocol version (required)",[172,994,995,998],{},[193,996,997],{},"idp=https://..."," — IdP URL (required)",[172,1000,1001,1004,1005,1008,1009,1012],{},[193,1002,1003],{},"mode=open"," — enrollment mode: ",[193,1006,1007],{},"open"," (anyone can register) or ",[193,1010,1011],{},"invite"," (registration URLs only)",[164,1014,1016],{"id":1015},"verify-dns","Verify DNS",[186,1018,1020],{"className":559,"code":1019,"language":561,"meta":195,"style":195},"dig _ddisa.example.com TXT +short\n# Expected: \"v=ddisa1 idp=https://id.example.com; mode=open\"\n",[193,1021,1022,1036],{"__ignoreMap":195},[217,1023,1024,1027,1030,1033],{"class":219,"line":220},[217,1025,1026],{"class":568},"dig",[217,1028,1029],{"class":257}," _ddisa.example.com",[217,1031,1032],{"class":257}," TXT",[217,1034,1035],{"class":257}," +short\n",[217,1037,1038],{"class":219,"line":242},[217,1039,1040],{"class":581},"# Expected: \"v=ddisa1 idp=https://id.example.com; mode=open\"\n",[526,1042,1044],{"type":1043},"info",[160,1045,1046,1047,1049,1050,1057],{},"DNS propagation can take up to 48 hours, but most providers propagate within minutes. Use ",[193,1048,1026],{}," or ",[1051,1052,1056],"a",{"href":1053,"rel":1054},"https://dnschecker.org",[1055],"nofollow","dnschecker.org"," to verify.",[155,1059,1061],{"id":1060},"s3-storage-configuration","S3 Storage Configuration",[160,1063,1064],{},"OpenApe supports any S3-compatible storage (AWS S3, MinIO, Cloudflare R2, DigitalOcean Spaces):",[186,1066,1068],{"className":211,"code":1067,"language":213,"meta":195,"style":195},"nitro: {\n  storage: {\n    'openape-idp': {\n      driver: 's3',\n      bucket: 'openape-data',\n      region: 'eu-central-1',\n      endpoint: 'https://s3.eu-central-1.amazonaws.com',  // Optional for AWS\n      accessKeyId: process.env.S3_ACCESS_KEY,\n      secretAccessKey: process.env.S3_SECRET_KEY\n    }\n  }\n}\n",[193,1069,1070,1079,1088,1102,1117,1133,1148,1168,1187,1204,1208,1212],{"__ignoreMap":195},[217,1071,1072,1075,1077],{"class":219,"line":220},[217,1073,1074],{"class":568},"nitro",[217,1076,208],{"class":238},[217,1078,276],{"class":238},[217,1080,1081,1084,1086],{"class":219,"line":242},[217,1082,1083],{"class":568},"  storage",[217,1085,208],{"class":238},[217,1087,276],{"class":238},[217,1089,1090,1093,1095,1097,1100],{"class":219,"line":198},[217,1091,1092],{"class":238},"    '",[217,1094,295],{"class":257},[217,1096,254],{"class":238},[217,1098,1099],{"class":245},": ",[217,1101,239],{"class":238},[217,1103,1104,1107,1109,1111,1113,1115],{"class":219,"line":279},[217,1105,1106],{"class":245},"      driver",[217,1108,208],{"class":238},[217,1110,312],{"class":238},[217,1112,315],{"class":257},[217,1114,254],{"class":238},[217,1116,266],{"class":238},[217,1118,1119,1122,1124,1126,1129,1131],{"class":219,"line":289},[217,1120,1121],{"class":245},"      bucket",[217,1123,208],{"class":238},[217,1125,312],{"class":238},[217,1127,1128],{"class":257},"openape-data",[217,1130,254],{"class":238},[217,1132,266],{"class":238},[217,1134,1135,1138,1140,1142,1144,1146],{"class":219,"line":304},[217,1136,1137],{"class":245},"      region",[217,1139,208],{"class":238},[217,1141,312],{"class":238},[217,1143,349],{"class":257},[217,1145,254],{"class":238},[217,1147,266],{"class":238},[217,1149,1150,1153,1155,1157,1160,1162,1165],{"class":219,"line":322},[217,1151,1152],{"class":245},"      endpoint",[217,1154,208],{"class":238},[217,1156,312],{"class":238},[217,1158,1159],{"class":257},"https://s3.eu-central-1.amazonaws.com",[217,1161,254],{"class":238},[217,1163,1164],{"class":238},",",[217,1166,1167],{"class":581},"  // Optional for AWS\n",[217,1169,1170,1173,1175,1177,1179,1181,1183,1185],{"class":219,"line":339},[217,1171,1172],{"class":245},"      accessKeyId",[217,1174,208],{"class":238},[217,1176,364],{"class":234},[217,1178,367],{"class":238},[217,1180,370],{"class":234},[217,1182,367],{"class":238},[217,1184,375],{"class":234},[217,1186,266],{"class":238},[217,1188,1189,1192,1194,1196,1198,1200,1202],{"class":219,"line":356},[217,1190,1191],{"class":245},"      secretAccessKey",[217,1193,208],{"class":238},[217,1195,364],{"class":234},[217,1197,367],{"class":238},[217,1199,370],{"class":234},[217,1201,367],{"class":238},[217,1203,396],{"class":234},[217,1205,1206],{"class":219,"line":380},[217,1207,509],{"class":238},[217,1209,1210],{"class":219,"line":399},[217,1211,515],{"class":238},[217,1213,1214],{"class":219,"line":405},[217,1215,1216],{"class":238},"}\n",[160,1218,1219,1220,1223],{},"For ",[175,1221,1222],{},"MinIO"," (self-hosted):",[186,1225,1227],{"className":211,"code":1226,"language":213,"meta":195,"style":195},"'openape-idp': {\n  driver: 's3',\n  bucket: 'openape',\n  endpoint: 'http://minio:9000',\n  accessKeyId: 'minioadmin',\n  secretAccessKey: 'minioadmin',\n  forcePathStyle: true  // Required for MinIO\n}\n",[193,1228,1229,1241,1256,1272,1288,1304,1319,1333],{"__ignoreMap":195},[217,1230,1231,1233,1235,1237,1239],{"class":219,"line":220},[217,1232,254],{"class":238},[217,1234,295],{"class":257},[217,1236,254],{"class":238},[217,1238,1099],{"class":234},[217,1240,239],{"class":238},[217,1242,1243,1246,1248,1250,1252,1254],{"class":219,"line":242},[217,1244,1245],{"class":245},"  driver",[217,1247,208],{"class":238},[217,1249,312],{"class":238},[217,1251,315],{"class":257},[217,1253,254],{"class":238},[217,1255,266],{"class":238},[217,1257,1258,1261,1263,1265,1268,1270],{"class":219,"line":198},[217,1259,1260],{"class":245},"  bucket",[217,1262,208],{"class":238},[217,1264,312],{"class":238},[217,1266,1267],{"class":257},"openape",[217,1269,254],{"class":238},[217,1271,266],{"class":238},[217,1273,1274,1277,1279,1281,1284,1286],{"class":219,"line":279},[217,1275,1276],{"class":245},"  endpoint",[217,1278,208],{"class":238},[217,1280,312],{"class":238},[217,1282,1283],{"class":257},"http://minio:9000",[217,1285,254],{"class":238},[217,1287,266],{"class":238},[217,1289,1290,1293,1295,1297,1300,1302],{"class":219,"line":289},[217,1291,1292],{"class":245},"  accessKeyId",[217,1294,208],{"class":238},[217,1296,312],{"class":238},[217,1298,1299],{"class":257},"minioadmin",[217,1301,254],{"class":238},[217,1303,266],{"class":238},[217,1305,1306,1309,1311,1313,1315,1317],{"class":219,"line":304},[217,1307,1308],{"class":245},"  secretAccessKey",[217,1310,208],{"class":238},[217,1312,312],{"class":238},[217,1314,1299],{"class":257},[217,1316,254],{"class":238},[217,1318,266],{"class":238},[217,1320,1321,1324,1326,1330],{"class":219,"line":322},[217,1322,1323],{"class":245},"  forcePathStyle",[217,1325,208],{"class":238},[217,1327,1329],{"class":1328},"sfNiH"," true",[217,1331,1332],{"class":581},"  // Required for MinIO\n",[217,1334,1335],{"class":219,"line":339},[217,1336,1216],{"class":238},[155,1338,1340],{"id":1339},"reverse-proxy-nginx-caddy","Reverse Proxy (nginx / Caddy)",[160,1342,1343],{},"If running behind a reverse proxy, ensure WebSocket and HTTPS headers are forwarded:",[164,1345,1347],{"id":1346},"caddy","Caddy",[186,1349,1352],{"className":1350,"code":1351,"language":191},[189],"id.example.com {\n  reverse_proxy localhost:3000\n}\n",[193,1353,1351],{"__ignoreMap":195},[164,1355,1356],{"id":1356},"nginx",[186,1358,1361],{"className":1359,"code":1360,"language":1356,"meta":195,"style":195},"language-nginx shiki shiki-themes material-theme-lighter material-theme material-theme-palenight","server {\n    server_name id.example.com;\n    listen 443 ssl;\n\n    location / {\n        proxy_pass http://localhost:3000;\n        proxy_set_header Host $host;\n        proxy_set_header X-Real-IP $remote_addr;\n        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;\n        proxy_set_header X-Forwarded-Proto $scheme;\n    }\n}\n",[193,1362,1363,1368,1373,1378,1382,1387,1392,1397,1402,1407,1412,1416],{"__ignoreMap":195},[217,1364,1365],{"class":219,"line":220},[217,1366,1367],{},"server {\n",[217,1369,1370],{"class":219,"line":242},[217,1371,1372],{},"    server_name id.example.com;\n",[217,1374,1375],{"class":219,"line":198},[217,1376,1377],{},"    listen 443 ssl;\n",[217,1379,1380],{"class":219,"line":279},[217,1381,761],{"emptyLinePlaceholder":760},[217,1383,1384],{"class":219,"line":289},[217,1385,1386],{},"    location / {\n",[217,1388,1389],{"class":219,"line":304},[217,1390,1391],{},"        proxy_pass http://localhost:3000;\n",[217,1393,1394],{"class":219,"line":322},[217,1395,1396],{},"        proxy_set_header Host $host;\n",[217,1398,1399],{"class":219,"line":339},[217,1400,1401],{},"        proxy_set_header X-Real-IP $remote_addr;\n",[217,1403,1404],{"class":219,"line":356},[217,1405,1406],{},"        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;\n",[217,1408,1409],{"class":219,"line":380},[217,1410,1411],{},"        proxy_set_header X-Forwarded-Proto $scheme;\n",[217,1413,1414],{"class":219,"line":399},[217,1415,509],{},[217,1417,1418],{"class":219,"line":405},[217,1419,1216],{},[155,1421,1423],{"id":1422},"production-checklist","Production Checklist",[164,1425,89],{"id":1426},"security",[985,1428,1431,1444,1453,1459,1465],{"className":1429},[1430],"contains-task-list",[172,1432,1435,1439,1440,1443],{"className":1433},[1434],"task-list-item",[1436,1437],"input",{"disabled":760,"type":1438},"checkbox"," Strong ",[193,1441,1442],{},"sessionSecret"," (32+ random characters)",[172,1445,1447,1439,1449,1452],{"className":1446},[1434],[1436,1448],{"disabled":760,"type":1438},[193,1450,1451],{},"managementToken"," (64+ random characters)",[172,1454,1456,1458],{"className":1455},[1434],[1436,1457],{"disabled":760,"type":1438}," Management Token stored in secrets manager, not in code",[172,1460,1462,1464],{"className":1461},[1434],[1436,1463],{"disabled":760,"type":1438}," HTTPS everywhere (required for Passkeys)",[172,1466,1468,1470],{"className":1467},[1434],[1436,1469],{"disabled":760,"type":1438}," DNSSEC enabled for your domain",[164,1472,1474],{"id":1473},"storage","Storage",[985,1476,1478,1484,1490],{"className":1477},[1430],[172,1479,1481,1483],{"className":1480},[1434],[1436,1482],{"disabled":760,"type":1438}," Persistent storage configured (S3, filesystem — NOT in-memory)",[172,1485,1487,1489],{"className":1486},[1434],[1436,1488],{"disabled":760,"type":1438}," Storage backups enabled",[172,1491,1493,1495],{"className":1492},[1434],[1436,1494],{"disabled":760,"type":1438}," Separate storage keys for IdP data and grants",[164,1497,1499],{"id":1498},"dns","DNS",[985,1501,1503,1512],{"className":1502},[1430],[172,1504,1506,1508,1509,1511],{"className":1505},[1434],[1436,1507],{"disabled":760,"type":1438}," ",[193,1510,542],{}," TXT record published and verified",[172,1513,1515,1517],{"className":1514},[1434],[1436,1516],{"disabled":760,"type":1438}," DNSSEC enabled (recommended)",[164,1519,142],{"id":1520},"monitoring",[985,1522,1524,1530,1536],{"className":1523},[1430],[172,1525,1527,1529],{"className":1526},[1434],[1436,1528],{"disabled":760,"type":1438}," Audit logs collected and retained",[172,1531,1533,1535],{"className":1532},[1434],[1436,1534],{"disabled":760,"type":1438}," Alerts on failed authentication attempts",[172,1537,1539,1541],{"className":1538},[1434],[1436,1540],{"disabled":760,"type":1438}," Alerts on denied grants",[1543,1544,1545],"style",{},"html pre.shiki code .s7zQu, html code.shiki .s7zQu{--shiki-light:#39ADB5;--shiki-light-font-style:italic;--shiki-default:#89DDFF;--shiki-default-font-style:italic;--shiki-dark:#89DDFF;--shiki-dark-font-style:italic}html pre.shiki code .s2Zo4, html code.shiki .s2Zo4{--shiki-light:#6182B8;--shiki-default:#82AAFF;--shiki-dark:#82AAFF}html pre.shiki code .sTEyZ, html code.shiki .sTEyZ{--shiki-light:#90A4AE;--shiki-default:#EEFFFF;--shiki-dark:#BABED8}html pre.shiki code .sMK4o, html code.shiki .sMK4o{--shiki-light:#39ADB5;--shiki-default:#89DDFF;--shiki-dark:#89DDFF}html pre.shiki code .swJcz, html code.shiki .swJcz{--shiki-light:#E53935;--shiki-default:#F07178;--shiki-dark:#F07178}html pre.shiki code .sfazB, html code.shiki .sfazB{--shiki-light:#91B859;--shiki-default:#C3E88D;--shiki-dark:#C3E88D}html .light .shiki span {color: var(--shiki-light);background: var(--shiki-light-bg);font-style: var(--shiki-light-font-style);font-weight: var(--shiki-light-font-weight);text-decoration: var(--shiki-light-text-decoration);}html.light .shiki span {color: var(--shiki-light);background: var(--shiki-light-bg);font-style: var(--shiki-light-font-style);font-weight: var(--shiki-light-font-weight);text-decoration: var(--shiki-light-text-decoration);}html .default .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .dark .shiki span {color: var(--shiki-dark);background: var(--shiki-dark-bg);font-style: var(--shiki-dark-font-style);font-weight: var(--shiki-dark-font-weight);text-decoration: var(--shiki-dark-text-decoration);}html.dark .shiki span {color: var(--shiki-dark);background: var(--shiki-dark-bg);font-style: var(--shiki-dark-font-style);font-weight: var(--shiki-dark-font-weight);text-decoration: var(--shiki-dark-text-decoration);}html pre.shiki code .sBMFI, html code.shiki .sBMFI{--shiki-light:#E2931D;--shiki-default:#FFCB6B;--shiki-dark:#FFCB6B}html pre.shiki code .sHwdD, html code.shiki .sHwdD{--shiki-light:#90A4AE;--shiki-light-font-style:italic;--shiki-default:#546E7A;--shiki-default-font-style:italic;--shiki-dark:#676E95;--shiki-dark-font-style:italic}html pre.shiki code .sfNiH, html code.shiki .sfNiH{--shiki-light:#FF5370;--shiki-default:#FF9CAC;--shiki-dark:#FF9CAC}",{"title":195,"searchDepth":198,"depth":242,"links":1547},[1548,1552,1556,1560,1561,1565],{"id":157,"depth":242,"text":158,"children":1549},[1550,1551],{"id":166,"depth":198,"text":167},{"id":585,"depth":198,"text":586},{"id":713,"depth":242,"text":714,"children":1553},[1554,1555],{"id":717,"depth":198,"text":718},{"id":793,"depth":198,"text":794},{"id":965,"depth":242,"text":966,"children":1557},[1558,1559],{"id":969,"depth":198,"text":970},{"id":1015,"depth":198,"text":1016},{"id":1060,"depth":242,"text":1061},{"id":1339,"depth":242,"text":1340,"children":1562},[1563,1564],{"id":1346,"depth":198,"text":1347},{"id":1356,"depth":198,"text":1356},{"id":1422,"depth":242,"text":1423,"children":1566},[1567,1568,1569,1570],{"id":1426,"depth":198,"text":89},{"id":1473,"depth":198,"text":1474},{"id":1498,"depth":198,"text":1499},{"id":1520,"depth":198,"text":142},"Deploy OpenApe IdP and SP to production.","md",null,{},{"title":134,"description":1571},"PWGBYTdPkkh5pOOzyYkbTUnxdBl3PpesMapd47bHwxQ",[1578,1580],{"title":128,"path":129,"stem":130,"description":1579,"children":-1},"Deployment, monitoring, and troubleshooting for production environments.",{"title":138,"path":139,"stem":140,"description":1581,"children":-1},"Common errors and their solutions.",1774221117377]