[{"data":1,"prerenderedAt":1202},["ShallowReactive",2],{"sidebar-posts":3,"post-count":78,"post-\u002Fhow-to-run-parse-dashboard-alongside-parse-server-on-digital-ocean":79,"page-\u002Fhow-to-run-parse-dashboard-alongside-parse-server-on-digital-ocean":1195,"neighbours-\u002Fhow-to-run-parse-dashboard-alongside-parse-server-on-digital-ocean":1197,"post-projects-\u002Fhow-to-run-parse-dashboard-alongside-parse-server-on-digital-ocean":1200},[4,8,12,16,19,23,27,31,35,39,43,47,50,54,58,62,66,70,74],{"path":5,"title":6,"date":7},"\u002Fbuilding-take-contentin-mobile-app","I built a ContentIn mobile app in one night and tested it from the sauna","2026-10-29",{"path":9,"title":10,"date":11},"\u002Fmac-mini-claude-code-dev-server","My Mac Mini is my dev server, and one Claude Code session runs each project","2026-10-27",{"path":13,"title":14,"date":15},"\u002Fmax-out-claude-code-every-week","Max out Claude Code every week until I make 10K a month","2026-10-26",{"path":17,"title":18,"date":15},"\u002Fmaxing-out-claude-code-week-1","Maxing out Claude Code, week 1: a new blog, an app stuck in review and a full Mac Mini",{"path":20,"title":21,"date":22},"\u002Ffully-ai-coded-blog-claude-code","This blog is now fully AI coded and run by an agent I just talk to","2026-10-24",{"path":24,"title":25,"date":26},"\u002Fwhy-i-built-pepelly","Why I built Pepelly, a YouTube app for my daughter without the brain rot","2026-10-22",{"path":28,"title":29,"date":30},"\u002Fhow-i-built-an-equity-tracking-app-for-bootstrap-founders-in-a-weekend","How I Built an Equity Tracking App for Bootstrap Founders in a Weekend","2024-11-25",{"path":32,"title":33,"date":34},"\u002Fbuilding-directory-website-with-ai-in-a-day","How I Built a Directory Website in a Day with AI—and Why It's a Game-Changer for SaaS Traffic","2024-11-10",{"path":36,"title":37,"date":38},"\u002Fnetlify-build-plugin-for-nuxt-dynamic-routes","Use a netlify build plugin to generate your nuxt routes","2020-08-08",{"path":40,"title":41,"date":42},"\u002Foptimized-responsive-lazyloading-images-with-nuxt","How to use optimized, responsive and lazyloading images in a nuxt project","2019-11-16",{"path":44,"title":45,"date":46},"\u002Fnuxt-jam-stack","Building a SEO optimized blog with a Nuxt JAM stack and Markdown files","2019-11-07",{"path":48,"title":49,"date":46},"\u002Fprismjs-nuxtjs-static-pages","Getting Prismjs working with Nuxt",{"path":51,"title":52,"date":53},"\u002Fkeylogs-live-on-producthunt","My second launch this year: Keylogs is LIVE on Product Hunt today!","2018-02-12",{"path":55,"title":56,"date":57},"\u002Fa-new-year-and-a-new-startup","A new year and a new startup","2018-01-19",{"path":59,"title":60,"date":61},"\u002Fabout-mydash-whats-the-stack-and-why-did-i-choose-it","About myDash - What’s the stack and why did I choose it?","2017-10-16",{"path":63,"title":64,"date":65},"\u002Fsuper-fast-wordpress-hosting-germany","WordPress hosting test: super fast on raidboxes.eu","2016-12-09",{"path":67,"title":68,"date":69},"\u002Fbest-resources-for-stock-images","Best resources for stock images","2016-12-05",{"path":71,"title":72,"date":73},"\u002Fset-up-automatic-backups-for-parse-server-on-digital-ocean","Set up automatic backups for parse-server on digital ocean","2016-05-25",{"path":75,"title":76,"date":77},"\u002Fhow-to-run-parse-dashboard-alongside-parse-server-on-digital-ocean","How to setup parse-dashboard alongside parse-server on Digital Ocean","2016-05-18",19,{"id":80,"title":76,"body":81,"date":77,"description":1183,"draft":1184,"extension":1185,"image":1186,"meta":1187,"navigation":191,"path":75,"projects":1188,"readingTime":188,"seo":1190,"stem":1191,"tags":1192,"updated":1195,"__hash__":1196},"posts\u002Fhow-to-run-parse-dashboard-alongside-parse-server-on-digital-ocean.md",{"type":82,"value":83,"toc":1174},"minimark",[84,96,108,113,118,125,129,140,153,163,321,336,733,736,741,745,748,1000,1010,1013,1042,1052,1056,1067,1153,1159,1163,1170],[85,86,87,88,95],"p",{},"In this post I'll explain how to set up parse-dashboard along with parse-server on the same ",[89,90,94],"a",{"href":91,"rel":92},"https:\u002F\u002Fm.do.co\u002Fc\u002Ff5a70d4a6dbb",[93],"nofollow","Digital Ocean droplet*"," (or any ubuntu\u002Fnginx server really).",[97,98,99],"blockquote",{},[85,100,101,102,107],{},"This guide is heavily based on the awesome tutorial by Digital Ocean on ",[89,103,106],{"href":104,"rel":105},"https:\u002F\u002Fwww.digitalocean.com\u002Fcommunity\u002Ftutorials\u002Fhow-to-migrate-a-parse-app-to-parse-server-on-ubuntu-14-04",[93],"how to setup and migrate parse-server to them",". I really recommend reading it before following along with my post. Basically what I do here starts where the tutorial stops.",[109,110,112],"h2",{"id":111},"setting-up-parse-dashboard-in-4-steps","Setting up parse-dashboard in 4 steps",[114,115,117],"h3",{"id":116},"_1-install-parse-dashboard","1. Install parse-dashboard",[85,119,120,121],{},"Obviously the first step is to install parse-dashboard with npm and your sudo user. Just do it globally like so:\n",[122,123,124],"code",{},"sudo npm install -g parse-dashboard",[114,126,128],{"id":127},"_2-set-up-a-new-indexjs-with-two-apps-for-server-and-dashboard","2. Set up a new index.js with two apps for server and dashboard",[85,130,131,132,135,136,139],{},"For this step switch to the parse user ",[122,133,134],{},"sudo su parse"," and go to the home folder ",[122,137,138],{},"cd ~",".",[85,141,142,143,148,149,152],{},"In the official ",[89,144,147],{"href":145,"rel":146},"https:\u002F\u002Fgithub.com\u002FParsePlatform\u002Fparse-dashboard#running-as-express-middleware",[93],"dashboard docs"," the guys from parse show how to use both the server and the dashboard in one app. With NGINX reverse proxy I found it easier to set up two apps running on different ports in the same ",[122,150,151],{},"index.js"," file.",[85,154,155,156,158,159,162],{},"In the digital ocean tutorial you didn't set up a index.js. So start by going to your home folder ",[122,157,138],{},"and create the file by entering ",[122,160,161],{},"nano index.js",".\nNow based on the official example on github put together the code for your parse-dashboard app like this:",[164,165,170],"pre",{"className":166,"code":167,"language":168,"meta":169,"style":169},"language-javascript shiki shiki-themes derkinzi-tomorrow-night","var express = require('express');\nvar ParseDashboard = require('parse-dashboard');\n\nvar dashboard = new ParseDashboard({\n  \"apps\": [{\n      \"serverURL\": \"http:\u002F\u002FPUBLICDOMAIN\u002Fparse\",\n      \"appId\": \"myAppId\",\n      \"masterKey\": \"myMasterKey\",\n      \"appName\": \"MyApp\"\n  }],\n  \"users\": [\n    {\n      \"user\":\"username\",\n      \"pass\":\"password\"\n    }\n  ],\n});\n\nvar dashApp = express();\n\n\u002F\u002F make the Parse Dashboard available at \u002Fdashboard\ndashApp.use('\u002Fdashboard', dashboard);\n\nvar httpServerDash = require('http').createServer(dashApp);\nhttpServerDash.listen(4040);\n","javascript","",[122,171,172,180,186,193,199,205,211,217,223,229,235,241,247,253,259,265,271,277,282,287,292,298,304,309,315],{"__ignoreMap":169},[173,174,177],"span",{"class":175,"line":176},"line",1,[173,178,179],{},"var express = require('express');\n",[173,181,183],{"class":175,"line":182},2,[173,184,185],{},"var ParseDashboard = require('parse-dashboard');\n",[173,187,189],{"class":175,"line":188},3,[173,190,192],{"emptyLinePlaceholder":191},true,"\n",[173,194,196],{"class":175,"line":195},4,[173,197,198],{},"var dashboard = new ParseDashboard({\n",[173,200,202],{"class":175,"line":201},5,[173,203,204],{},"  \"apps\": [{\n",[173,206,208],{"class":175,"line":207},6,[173,209,210],{},"      \"serverURL\": \"http:\u002F\u002FPUBLICDOMAIN\u002Fparse\",\n",[173,212,214],{"class":175,"line":213},7,[173,215,216],{},"      \"appId\": \"myAppId\",\n",[173,218,220],{"class":175,"line":219},8,[173,221,222],{},"      \"masterKey\": \"myMasterKey\",\n",[173,224,226],{"class":175,"line":225},9,[173,227,228],{},"      \"appName\": \"MyApp\"\n",[173,230,232],{"class":175,"line":231},10,[173,233,234],{},"  }],\n",[173,236,238],{"class":175,"line":237},11,[173,239,240],{},"  \"users\": [\n",[173,242,244],{"class":175,"line":243},12,[173,245,246],{},"    {\n",[173,248,250],{"class":175,"line":249},13,[173,251,252],{},"      \"user\":\"username\",\n",[173,254,256],{"class":175,"line":255},14,[173,257,258],{},"      \"pass\":\"password\"\n",[173,260,262],{"class":175,"line":261},15,[173,263,264],{},"    }\n",[173,266,268],{"class":175,"line":267},16,[173,269,270],{},"  ],\n",[173,272,274],{"class":175,"line":273},17,[173,275,276],{},"});\n",[173,278,280],{"class":175,"line":279},18,[173,281,192],{"emptyLinePlaceholder":191},[173,283,284],{"class":175,"line":78},[173,285,286],{},"var dashApp = express();\n",[173,288,290],{"class":175,"line":289},20,[173,291,192],{"emptyLinePlaceholder":191},[173,293,295],{"class":175,"line":294},21,[173,296,297],{},"\u002F\u002F make the Parse Dashboard available at \u002Fdashboard\n",[173,299,301],{"class":175,"line":300},22,[173,302,303],{},"dashApp.use('\u002Fdashboard', dashboard);\n",[173,305,307],{"class":175,"line":306},23,[173,308,192],{"emptyLinePlaceholder":191},[173,310,312],{"class":175,"line":311},24,[173,313,314],{},"var httpServerDash = require('http').createServer(dashApp);\n",[173,316,318],{"class":175,"line":317},25,[173,319,320],{},"httpServerDash.listen(4040);\n",[85,322,323,324,329,330,335],{},"Make sure you use your real domain as serverURL. Not localhost and not your IP. Also make sure you set a different port for this app. If you stick with default it's 4040. You can find additional config options like adding icons, more apps and user ",[89,325,328],{"href":326,"rel":327},"https:\u002F\u002Fgithub.com\u002FParsePlatform\u002Fparse-dashboard#configuring-basic-authentication",[93],"here",".\nNow we need to put our parse-server app configuration into the same file. The following code is again based on the parse ",[89,331,334],{"href":332,"rel":333},"https:\u002F\u002Fgithub.com\u002FParsePlatform\u002Fparse-server\u002Fwiki\u002FParse-Server-Guide#usage",[93],"documentation on github",". Here are server and dashboard together:",[164,337,339],{"className":166,"code":338,"language":168,"meta":169,"style":169},"\u002F\u002F Packtor Server\nvar express = require('express');  \nvar ParseServer = require('parse-server').ParseServer;\nvar ParseDashboard = require('parse-dashboard');  \nvar path = require('path');  \n\nvar databaseUri = process.env.DATABASE_URI || process.env.MONGODB_URI;\n\nif (!databaseUri) {  \n  console.log('DATABASE_URI not specified, falling back to localhost.');\n}\n\n\u002F\u002F Set up parse server\nvar api = new ParseServer({  \n  databaseURI: databaseUri || 'mongodb:\u002F\u002FUSER:PASSWORD@DOMAIN:27017\u002FDB_NAME?ssl=true',\n  cloud: process.env.CLOUD_CODE_MAIN || __dirname + '\u002Fcloud\u002Fmain.js',\n  appId: process.env.APP_ID || 'YOUR_KEY',\n  masterKey: process.env.MASTER_KEY || 'YOUR_KEY',\n  serverURL: process.env.SERVER_URL || 'http:\u002F\u002Flocalhost:1337\u002Fparse'\n});\n\nvar app = express();\n\n\u002F\u002F Serve static assets from the \u002Fpublic folder\napp.use('\u002Fpublic', express.static(path.join(__dirname, '\u002Fpublic')));\n\n\u002F\u002F Serve the Parse API on the \u002Fparse URL prefix\nvar mountPath = process.env.PARSE_MOUNT || '\u002Fparse';  \napp.use(mountPath, api);\n\n\u002F\u002F Parse Server plays nicely with the rest of your web routes\napp.get('\u002F', function(req, res) {  \n  res.status(200).send('Parse Server App');\n});\n\nvar port = process.env.PORT || 1337;  \nvar httpServer = require('http').createServer(app);  \nhttpServer.listen(port, function() {  \n    console.log('packtor-server running on port ' + port + '.');\n});\n\n\u002F\u002F Set up parse dashboard\nvar dashboard = new ParseDashboard({  \n  \"apps\": [{\n      \"serverURL\": 'https:\u002F\u002FPUBLIC_DOMAIN\u002Fparse', \u002F\u002F Not localhost\n      \"appId\": 'YOUR_KEY',\n      \"masterKey\": 'YOUR_KEY',\n      \"appName\": \"YourAppName\",\n      \"production\": false,\n      \"iconName\": \"app-icon.png\",\n  }],\n  \"users\": [\n    {\n      \"user\":\"username\",\n      \"pass\":\"password\"\n    }\n  ],\n  \"iconsFolder\": \"icons\"\n});\n\nvar dashApp = express();\n\n\u002F\u002F make the Parse Dashboard available at \u002Fdashboard\ndashApp.use('\u002Fdashboard', dashboard);  \n\n\u002F\u002F Parse Server plays nicely with the rest of your web routes\ndashApp.get('\u002F', function(req, res) {  \n  res.status(200).send('Parse Dashboard App');\n});\n\nvar httpServerDash = require('http').createServer(dashApp);  \nhttpServerDash.listen(4040, function() {  \n    console.log('dashboard-server running on port 4040.');\n});\n",[122,340,341,346,351,356,361,366,370,375,379,384,389,394,398,403,408,413,418,423,428,433,437,441,446,450,455,460,465,471,477,483,488,494,500,506,511,516,522,528,534,540,545,550,556,562,567,576,582,588,594,600,606,611,616,621,626,631,636,641,647,652,657,662,667,672,678,683,688,694,700,705,710,716,722,728],{"__ignoreMap":169},[173,342,343],{"class":175,"line":176},[173,344,345],{},"\u002F\u002F Packtor Server\n",[173,347,348],{"class":175,"line":182},[173,349,350],{},"var express = require('express');  \n",[173,352,353],{"class":175,"line":188},[173,354,355],{},"var ParseServer = require('parse-server').ParseServer;\n",[173,357,358],{"class":175,"line":195},[173,359,360],{},"var ParseDashboard = require('parse-dashboard');  \n",[173,362,363],{"class":175,"line":201},[173,364,365],{},"var path = require('path');  \n",[173,367,368],{"class":175,"line":207},[173,369,192],{"emptyLinePlaceholder":191},[173,371,372],{"class":175,"line":213},[173,373,374],{},"var databaseUri = process.env.DATABASE_URI || process.env.MONGODB_URI;\n",[173,376,377],{"class":175,"line":219},[173,378,192],{"emptyLinePlaceholder":191},[173,380,381],{"class":175,"line":225},[173,382,383],{},"if (!databaseUri) {  \n",[173,385,386],{"class":175,"line":231},[173,387,388],{},"  console.log('DATABASE_URI not specified, falling back to localhost.');\n",[173,390,391],{"class":175,"line":237},[173,392,393],{},"}\n",[173,395,396],{"class":175,"line":243},[173,397,192],{"emptyLinePlaceholder":191},[173,399,400],{"class":175,"line":249},[173,401,402],{},"\u002F\u002F Set up parse server\n",[173,404,405],{"class":175,"line":255},[173,406,407],{},"var api = new ParseServer({  \n",[173,409,410],{"class":175,"line":261},[173,411,412],{},"  databaseURI: databaseUri || 'mongodb:\u002F\u002FUSER:PASSWORD@DOMAIN:27017\u002FDB_NAME?ssl=true',\n",[173,414,415],{"class":175,"line":267},[173,416,417],{},"  cloud: process.env.CLOUD_CODE_MAIN || __dirname + '\u002Fcloud\u002Fmain.js',\n",[173,419,420],{"class":175,"line":273},[173,421,422],{},"  appId: process.env.APP_ID || 'YOUR_KEY',\n",[173,424,425],{"class":175,"line":279},[173,426,427],{},"  masterKey: process.env.MASTER_KEY || 'YOUR_KEY',\n",[173,429,430],{"class":175,"line":78},[173,431,432],{},"  serverURL: process.env.SERVER_URL || 'http:\u002F\u002Flocalhost:1337\u002Fparse'\n",[173,434,435],{"class":175,"line":289},[173,436,276],{},[173,438,439],{"class":175,"line":294},[173,440,192],{"emptyLinePlaceholder":191},[173,442,443],{"class":175,"line":300},[173,444,445],{},"var app = express();\n",[173,447,448],{"class":175,"line":306},[173,449,192],{"emptyLinePlaceholder":191},[173,451,452],{"class":175,"line":311},[173,453,454],{},"\u002F\u002F Serve static assets from the \u002Fpublic folder\n",[173,456,457],{"class":175,"line":317},[173,458,459],{},"app.use('\u002Fpublic', express.static(path.join(__dirname, '\u002Fpublic')));\n",[173,461,463],{"class":175,"line":462},26,[173,464,192],{"emptyLinePlaceholder":191},[173,466,468],{"class":175,"line":467},27,[173,469,470],{},"\u002F\u002F Serve the Parse API on the \u002Fparse URL prefix\n",[173,472,474],{"class":175,"line":473},28,[173,475,476],{},"var mountPath = process.env.PARSE_MOUNT || '\u002Fparse';  \n",[173,478,480],{"class":175,"line":479},29,[173,481,482],{},"app.use(mountPath, api);\n",[173,484,486],{"class":175,"line":485},30,[173,487,192],{"emptyLinePlaceholder":191},[173,489,491],{"class":175,"line":490},31,[173,492,493],{},"\u002F\u002F Parse Server plays nicely with the rest of your web routes\n",[173,495,497],{"class":175,"line":496},32,[173,498,499],{},"app.get('\u002F', function(req, res) {  \n",[173,501,503],{"class":175,"line":502},33,[173,504,505],{},"  res.status(200).send('Parse Server App');\n",[173,507,509],{"class":175,"line":508},34,[173,510,276],{},[173,512,514],{"class":175,"line":513},35,[173,515,192],{"emptyLinePlaceholder":191},[173,517,519],{"class":175,"line":518},36,[173,520,521],{},"var port = process.env.PORT || 1337;  \n",[173,523,525],{"class":175,"line":524},37,[173,526,527],{},"var httpServer = require('http').createServer(app);  \n",[173,529,531],{"class":175,"line":530},38,[173,532,533],{},"httpServer.listen(port, function() {  \n",[173,535,537],{"class":175,"line":536},39,[173,538,539],{},"    console.log('packtor-server running on port ' + port + '.');\n",[173,541,543],{"class":175,"line":542},40,[173,544,276],{},[173,546,548],{"class":175,"line":547},41,[173,549,192],{"emptyLinePlaceholder":191},[173,551,553],{"class":175,"line":552},42,[173,554,555],{},"\u002F\u002F Set up parse dashboard\n",[173,557,559],{"class":175,"line":558},43,[173,560,561],{},"var dashboard = new ParseDashboard({  \n",[173,563,565],{"class":175,"line":564},44,[173,566,204],{},[173,568,570,573],{"class":175,"line":569},45,[173,571,572],{},"      \"serverURL\": 'https:\u002F\u002FPUBLIC_DOMAIN\u002Fparse',",[173,574,575],{}," \u002F\u002F Not localhost\n",[173,577,579],{"class":175,"line":578},46,[173,580,581],{},"      \"appId\": 'YOUR_KEY',\n",[173,583,585],{"class":175,"line":584},47,[173,586,587],{},"      \"masterKey\": 'YOUR_KEY',\n",[173,589,591],{"class":175,"line":590},48,[173,592,593],{},"      \"appName\": \"YourAppName\",\n",[173,595,597],{"class":175,"line":596},49,[173,598,599],{},"      \"production\": false,\n",[173,601,603],{"class":175,"line":602},50,[173,604,605],{},"      \"iconName\": \"app-icon.png\",\n",[173,607,609],{"class":175,"line":608},51,[173,610,234],{},[173,612,614],{"class":175,"line":613},52,[173,615,240],{},[173,617,619],{"class":175,"line":618},53,[173,620,246],{},[173,622,624],{"class":175,"line":623},54,[173,625,252],{},[173,627,629],{"class":175,"line":628},55,[173,630,258],{},[173,632,634],{"class":175,"line":633},56,[173,635,264],{},[173,637,639],{"class":175,"line":638},57,[173,640,270],{},[173,642,644],{"class":175,"line":643},58,[173,645,646],{},"  \"iconsFolder\": \"icons\"\n",[173,648,650],{"class":175,"line":649},59,[173,651,276],{},[173,653,655],{"class":175,"line":654},60,[173,656,192],{"emptyLinePlaceholder":191},[173,658,660],{"class":175,"line":659},61,[173,661,286],{},[173,663,665],{"class":175,"line":664},62,[173,666,192],{"emptyLinePlaceholder":191},[173,668,670],{"class":175,"line":669},63,[173,671,297],{},[173,673,675],{"class":175,"line":674},64,[173,676,677],{},"dashApp.use('\u002Fdashboard', dashboard);  \n",[173,679,681],{"class":175,"line":680},65,[173,682,192],{"emptyLinePlaceholder":191},[173,684,686],{"class":175,"line":685},66,[173,687,493],{},[173,689,691],{"class":175,"line":690},67,[173,692,693],{},"dashApp.get('\u002F', function(req, res) {  \n",[173,695,697],{"class":175,"line":696},68,[173,698,699],{},"  res.status(200).send('Parse Dashboard App');\n",[173,701,703],{"class":175,"line":702},69,[173,704,276],{},[173,706,708],{"class":175,"line":707},70,[173,709,192],{"emptyLinePlaceholder":191},[173,711,713],{"class":175,"line":712},71,[173,714,715],{},"var httpServerDash = require('http').createServer(dashApp);  \n",[173,717,719],{"class":175,"line":718},72,[173,720,721],{},"httpServerDash.listen(4040, function() {  \n",[173,723,725],{"class":175,"line":724},73,[173,726,727],{},"    console.log('dashboard-server running on port 4040.');\n",[173,729,731],{"class":175,"line":730},74,[173,732,276],{},[85,734,735],{},"That's it. Just copy the above into your index.js, edit your keys and variables and save the file.",[97,737,738],{},[85,739,740],{},"Hint: If you copy from github and don't use LiveQuery make sure you delete it from your code. It will result in poor api performance with the client SDK otherwise.",[114,742,744],{"id":743},"_3-changing-pm2-process","3. Changing pm2 process",[85,746,747],{},"In the Digital Ocean Guide the original pm2 config setup look like this:",[164,749,753],{"className":750,"code":751,"language":752,"meta":169,"style":169},"language-json shiki shiki-themes derkinzi-tomorrow-night","{\n  \"apps\" : [{\n    \"name\"        : \"parse-wrapper\",\n    \"script\"      : \"\u002Fusr\u002Fbin\u002Fparse-server\",  \u002F\u002F CHANGE THIS\n    \"watch\"       : true,\n    \"watch\"       : true,\n    \"merge_logs\"  : true,\n    \"cwd\"         : \"\u002Fhome\u002Fparse\",\n    \"env\": {\n      \"CLOUD_CODE_MAIN\": \"\u002Fhome\u002Fparse\u002Fcloud\u002Fmain.js\",\n      \"DATABASE_URI\": \"mongodb:\u002F\u002FUSER:PASSWORD@SOMAIN:27017\u002FDB-NAME?ssl=true\",\n      \"APPLICATION_ID\": \"APP_KEY\",\n      \"MASTER_KEY\": \"MASTER_KEY\"\n    }\n  }]\n}\n","json",[122,754,755,761,776,800,826,844,858,874,895,907,929,949,969,987,991,996],{"__ignoreMap":169},[173,756,757],{"class":175,"line":176},[173,758,760],{"class":759},"s2jRq","{\n",[173,762,763,766,770,773],{"class":175,"line":182},[173,764,765],{"class":759},"  \"",[173,767,769],{"class":768},"sJEhD","apps",[173,771,772],{"class":759},"\"",[173,774,775],{"class":759}," : [{\n",[173,777,778,781,784,786,789,791,795,797],{"class":175,"line":188},[173,779,780],{"class":759},"    \"",[173,782,783],{"class":768},"name",[173,785,772],{"class":759},[173,787,788],{"class":759},"        : ",[173,790,772],{"class":759},[173,792,794],{"class":793},"sRYIx","parse-wrapper",[173,796,772],{"class":759},[173,798,799],{"class":759},",\n",[173,801,802,804,807,809,812,814,817,819,822],{"class":175,"line":195},[173,803,780],{"class":759},[173,805,806],{"class":768},"script",[173,808,772],{"class":759},[173,810,811],{"class":759},"      : ",[173,813,772],{"class":759},[173,815,816],{"class":793},"\u002Fusr\u002Fbin\u002Fparse-server",[173,818,772],{"class":759},[173,820,821],{"class":759},",  ",[173,823,825],{"class":824},"sUXBo","\u002F\u002F CHANGE THIS\n",[173,827,828,830,833,835,838,842],{"class":175,"line":201},[173,829,780],{"class":759},[173,831,832],{"class":768},"watch",[173,834,772],{"class":759},[173,836,837],{"class":759},"       : ",[173,839,841],{"class":840},"s8nuv","true",[173,843,799],{"class":759},[173,845,846,848,850,852,854,856],{"class":175,"line":207},[173,847,780],{"class":759},[173,849,832],{"class":768},[173,851,772],{"class":759},[173,853,837],{"class":759},[173,855,841],{"class":840},[173,857,799],{"class":759},[173,859,860,862,865,867,870,872],{"class":175,"line":213},[173,861,780],{"class":759},[173,863,864],{"class":768},"merge_logs",[173,866,772],{"class":759},[173,868,869],{"class":759},"  : ",[173,871,841],{"class":840},[173,873,799],{"class":759},[173,875,876,878,881,883,886,888,891,893],{"class":175,"line":219},[173,877,780],{"class":759},[173,879,880],{"class":768},"cwd",[173,882,772],{"class":759},[173,884,885],{"class":759},"         : ",[173,887,772],{"class":759},[173,889,890],{"class":793},"\u002Fhome\u002Fparse",[173,892,772],{"class":759},[173,894,799],{"class":759},[173,896,897,899,902,904],{"class":175,"line":225},[173,898,780],{"class":759},[173,900,901],{"class":768},"env",[173,903,772],{"class":759},[173,905,906],{"class":759},": {\n",[173,908,909,912,915,917,920,922,925,927],{"class":175,"line":231},[173,910,911],{"class":759},"      \"",[173,913,914],{"class":768},"CLOUD_CODE_MAIN",[173,916,772],{"class":759},[173,918,919],{"class":759},": ",[173,921,772],{"class":759},[173,923,924],{"class":793},"\u002Fhome\u002Fparse\u002Fcloud\u002Fmain.js",[173,926,772],{"class":759},[173,928,799],{"class":759},[173,930,931,933,936,938,940,942,945,947],{"class":175,"line":237},[173,932,911],{"class":759},[173,934,935],{"class":768},"DATABASE_URI",[173,937,772],{"class":759},[173,939,919],{"class":759},[173,941,772],{"class":759},[173,943,944],{"class":793},"mongodb:\u002F\u002FUSER:PASSWORD@SOMAIN:27017\u002FDB-NAME?ssl=true",[173,946,772],{"class":759},[173,948,799],{"class":759},[173,950,951,953,956,958,960,962,965,967],{"class":175,"line":243},[173,952,911],{"class":759},[173,954,955],{"class":768},"APPLICATION_ID",[173,957,772],{"class":759},[173,959,919],{"class":759},[173,961,772],{"class":759},[173,963,964],{"class":793},"APP_KEY",[173,966,772],{"class":759},[173,968,799],{"class":759},[173,970,971,973,976,978,980,982,984],{"class":175,"line":249},[173,972,911],{"class":759},[173,974,975],{"class":768},"MASTER_KEY",[173,977,772],{"class":759},[173,979,919],{"class":759},[173,981,772],{"class":759},[173,983,975],{"class":793},[173,985,986],{"class":759},"\"\n",[173,988,989],{"class":175,"line":255},[173,990,264],{"class":759},[173,992,993],{"class":175,"line":261},[173,994,995],{"class":759},"  }]\n",[173,997,998],{"class":175,"line":267},[173,999,393],{"class":759},[85,1001,1002,1003,1006,1007],{},"When this fires it will start parse server not with a index.js file, but rather directly from the parse-server folder. This is not what we want so do ",[122,1004,1005],{},"nano ecosystem.json"," and change the 4th line to: ",[122,1008,1009],{},"\"script\" : \"\u002Fhome\u002Fparse\u002Findex.js\"",[85,1011,1012],{},"Now we are set and can restart pm2. Unfortunately only restarting pm2 doesn't take our updated ecosystems.json for some reason. So we need to delete the process first:",[164,1014,1018],{"className":1015,"code":1016,"language":1017,"meta":169,"style":169},"language-bash shiki shiki-themes derkinzi-tomorrow-night","pm2 delete all\npm2 start ecosystem.json\n","bash",[122,1019,1020,1032],{"__ignoreMap":169},[173,1021,1022,1026,1029],{"class":175,"line":176},[173,1023,1025],{"class":1024},"sHQA9","pm2",[173,1027,1028],{"class":793}," delete",[173,1030,1031],{"class":793}," all\n",[173,1033,1034,1036,1039],{"class":175,"line":182},[173,1035,1025],{"class":1024},[173,1037,1038],{"class":793}," start",[173,1040,1041],{"class":793}," ecosystem.json\n",[85,1043,1044,1045,1048,1049],{},"You can check with ",[122,1046,1047],{},"pm2 show 0"," if it started up correctly using index.js. Now just save the process: ",[122,1050,1051],{},"pm2 save",[114,1053,1055],{"id":1054},"_4-changing-nginx-setup","4. Changing nginx setup",[85,1057,1058,1059,1062,1063,1066],{},"The last step is to add the dashboard route to NGINX. ",[122,1060,1061],{},"exit"," into your sudo user. Then type ",[122,1064,1065],{},"sudo nano \u002Fetc\u002Fnginx\u002Fsites-enabled\u002Fdefault"," to get to the config file. Basically just copy the settings from parse-server, change the port to 4040 and paste it below the \u002Fparse route:",[164,1068,1072],{"className":1069,"code":1070,"language":1071,"meta":169,"style":169},"language-nginx shiki shiki-themes derkinzi-tomorrow-night","# Pass requests for \u002Fdashboard\u002F to Parse Server instance at localhost:4040\nlocation \u002Fdashboard\u002F {\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-NginX-Proxy true;\n         proxy_pass http:\u002F\u002Flocalhost:4040\u002Fdashboard\u002F;\n         proxy_ssl_session_reuse off;\n         proxy_set_header Host $http_host;\n         proxy_redirect off;\n}\n","nginx",[122,1073,1074,1079,1088,1096,1103,1115,1123,1133,1140,1149],{"__ignoreMap":169},[173,1075,1076],{"class":175,"line":176},[173,1077,1078],{"class":824},"# Pass requests for \u002Fdashboard\u002F to Parse Server instance at localhost:4040\n",[173,1080,1081,1085],{"class":175,"line":182},[173,1082,1084],{"class":1083},"sm2d5","location",[173,1086,1087],{"class":759}," \u002Fdashboard\u002F {\n",[173,1089,1090,1093],{"class":175,"line":188},[173,1091,1092],{"class":1083},"         proxy_set_header ",[173,1094,1095],{"class":759},"X-Real-IP $remote_addr;\n",[173,1097,1098,1100],{"class":175,"line":195},[173,1099,1092],{"class":1083},[173,1101,1102],{"class":759},"X-Forwarded-For $proxy_add_x_forwarded_for;\n",[173,1104,1105,1107,1110,1112],{"class":175,"line":201},[173,1106,1092],{"class":1083},[173,1108,1109],{"class":759},"X-NginX-Proxy ",[173,1111,841],{"class":840},[173,1113,1114],{"class":759},";\n",[173,1116,1117,1120],{"class":175,"line":207},[173,1118,1119],{"class":1083},"         proxy_pass ",[173,1121,1122],{"class":759},"http:\u002F\u002Flocalhost:4040\u002Fdashboard\u002F;\n",[173,1124,1125,1128,1131],{"class":175,"line":213},[173,1126,1127],{"class":1083},"         proxy_ssl_session_reuse ",[173,1129,1130],{"class":840},"off",[173,1132,1114],{"class":759},[173,1134,1135,1137],{"class":175,"line":219},[173,1136,1092],{"class":1083},[173,1138,1139],{"class":759},"Host $http_host;\n",[173,1141,1142,1145,1147],{"class":175,"line":225},[173,1143,1144],{"class":1083},"         proxy_redirect ",[173,1146,1130],{"class":840},[173,1148,1114],{"class":759},[173,1150,1151],{"class":175,"line":231},[173,1152,393],{"class":759},[85,1154,1155,1156],{},"Finally restart nginx: ",[122,1157,1158],{},"sudo service nginx restart",[109,1160,1162],{"id":1161},"done","Done",[85,1164,1165,1166,1169],{},"That's it: your parse-dashboard should be up and running on ",[122,1167,1168],{},"https:\u002F\u002Fyour.doma.in\u002Fdashboard",". Enjoy!",[1171,1172,1173],"style",{},"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 pre.shiki code .s2jRq, html code.shiki .s2jRq{--shiki-default:#CCCCCC}html pre.shiki code .sJEhD, html code.shiki .sJEhD{--shiki-default:#F8C555}html pre.shiki code .sRYIx, html code.shiki .sRYIx{--shiki-default:#7EC699}html pre.shiki code .sUXBo, html code.shiki .sUXBo{--shiki-default:#999999;--shiki-default-font-style:italic}html pre.shiki code .s8nuv, html code.shiki .s8nuv{--shiki-default:#F08D49}html pre.shiki code .sHQA9, html code.shiki .sHQA9{--shiki-default:#6196CC}html pre.shiki code .sm2d5, html code.shiki .sm2d5{--shiki-default:#CC99CD}",{"title":169,"searchDepth":182,"depth":188,"links":1175},[1176,1182],{"id":111,"depth":182,"text":112,"children":1177},[1178,1179,1180,1181],{"id":116,"depth":188,"text":117},{"id":127,"depth":188,"text":128},{"id":743,"depth":188,"text":744},{"id":1054,"depth":188,"text":1055},{"id":1161,"depth":182,"text":1162},"How to set up parse-dashboard next to parse-server on the same Digital Ocean droplet (or any Ubuntu\u002Fnginx server) in four steps.",false,"md","\u002Fimg\u002Fparse-dashboard-server-2.jpg",{},[1189],"packtor",{"title":76,"description":1183},"how-to-run-parse-dashboard-alongside-parse-server-on-digital-ocean",[1193,1194],"server","parse",null,"-9oiOqkdPWDi_XfLgZBVV18vgy2lZqI-90CRXZaZTdU",[1198,1195],{"title":72,"path":71,"stem":1199,"children":-1},"set-up-automatic-backups-for-parse-server-on-digital-ocean",[1201],{"id":1189,"title":1189},1793264868677]