Self-hosting Feedbin with Docker and OpenShift
Feedbin is an excellent RSS feed reader. You can sign up for its service and support its development. The company is gracious enough to offer its source code for DIYers to play with.
Prerequisites
API keys for Stripe and Skylight are required for running Feedbin. In addition, you need to pick a password for the PostgreSQL database. Populate the information in these two files:
db.env:
POSTGRES_PASSWORD=ChangeMe! POSTGRES_DB=feedbin POSTGRES_USER=feedbin
secrets.env:
PUSH_URL=http://feedbin.yourdomain.tls SECRET_KEY_BASE=48_bit_secret SKYLIGHT_AUTHENTICATION= STRIPE_API_KEY= STRIPE_PUBLIC_KEY=
Running Feedbin with Docker
You can find two Docker images here and here. The first image has to be used together with postgres, redis, memcached, elasticsearch, and nginx. The second image is all-in-one, minus postgres.
For the all-in-one image, you just need docker-compose.yml below in the same directory as the two files above. Then, run docker-compose up -d, and your Feedbin instance can be found at http://localhost:3000
docker-compose.yml:
version: '3' services: db: image: postgres:10.4 restart: always env_file: - db.env volumes: - db:/var/lib/postgresql/data app: image: rocwhite/feedbin-aio restart: always environment: - POSTGRES_HOST=db env_file: - db.env - secrets.env volumes: - app:/srv/apps/feedbin/current/public depends_on: - db volumes: db: es: app:
With the other image, use this docker-compose.yml instead, along with a nginx.conf file.
docker-compose.yml:
version: '3' services: db: image: postgres:10.4 restart: always env_file: - db.env volumes: - db:/var/lib/postgresql/data rds: image: redis:3.2 restart: always mcd: image: memcached:1.5 restart: always es: image: elasticsearch:2.4 restart: always volumes: - es:/usr/share/elasticsearch/data app: image: rocwhite/feedbin restart: always environment: - POSTGRES_HOST=db - MEMCACHED_HOST=mcd - REDIS_HOST=rds - ELASTIC_SEARCH_HOST=es env_file: - db.env - secrets.env volumes: - app:/srv/apps/feedbin/current/public depends_on: - db - rds - mcd - es web: image: nginx restart: always volumes: - app:/srv/apps/feedbin/current/public:ro - ./nginx.conf:/etc/nginx/conf.d/default.conf:ro depends_on: - app volumes: db: es: app:
nginx.conf:
## Lines starting with two hashes (##) are comments with information. ## Lines starting with one hash (#) are configuration parameters that can be uncommented. ## ################################### ## configuration ## ################################### ## ## See installation.md#using-https for additional HTTPS configuration details. upstream app { server app:3000; } ## Normal HTTP host server { listen 0.0.0.0:80 default_server; listen [::]:80 ipv6only=on default_server; server_tokens off; ## Don't show the nginx version number, a security best practice root /srv/apps/feedbin/current/public; ## Increase this if you want to upload large attachments client_max_body_size 20m; ## Individual nginx logs for this vhost access_log /var/log/nginx/access.log; error_log /var/log/nginx/error.log; location / { ## Serve static files from defined root folder. ## @app is a named location for the upstream fallback, see below. try_files $uri $uri/index.html $uri.html @app; } ## If a file, which is not found in the root folder is requested, ## then the proxy passes the request to the upsteam (unicorn). location @app { ## If you use HTTPS make sure you disable gzip compression ## to be safe against BREACH attack. # gzip off; proxy_read_timeout 300; proxy_connect_timeout 300; proxy_redirect off; proxy_set_header Host $http_host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header X-Forwarded-Proto $scheme; proxy_set_header X-Frame-Options SAMEORIGIN; proxy_pass http://app; } ## Enable gzip compression as per rails guide: ## http://guides.rubyonrails.org/asset_pipeline.html#gzip-compression ## WARNING: If you are using relative urls remove the block below ## See config/application.rb under "Relative url support" for the list of ## other files that need to be changed for relative url support location /assets/ { gzip_static on; # to serve pre-gzipped version expires max; add_header Cache-Control public; } error_page 502 /502.html; }
Running Feedbin on OpenShift
You probably need a Pro instance with > 1GB memory to run Feedbin. Once you create a new project, import db.env and secrets.env (see above) as secrets:
oc create secret generic feedbin-db --from-env-file=./db.env --type=opaque oc create secret generic feedbin-secrets --from-env-file=./secrets.env --type=opaque
Then create a new app using the template file below.
oc new-app -f ./openshift-aio.yml
openshift-aio.yml
apiVersion: v1 kind: Template metadata: name: feedbin objects: - apiVersion: v1 kind: PersistentVolumeClaim metadata: name: data spec: accessModes: - ReadWriteOnce resources: requests: storage: 1Gi - apiVersion: v1 kind: ImageStream metadata: labels: app: feedbin name: feedbin spec: lookupPolicy: local: false tags: - from: kind: DockerImage name: rocwhite/feedbin-aio importPolicy: {} name: latest referencePolicy: type: Source - apiVersion: v1 kind: DeploymentConfig metadata: labels: name: feedbin name: feedbin spec: replicas: 1 selector: deploymentconfig: feedbin strategy: activeDeadlineSeconds: 21600 recreateParams: timeoutSeconds: 600 resources: {} type: Recreate template: metadata: name: feedbin labels: name: feedbin deploymentconfig: feedbin spec: containers: - name: db image: registry.access.redhat.com/rhscl/postgresql-10-rhel7 env: - name: POSTGRESQL_DATABASE valueFrom: secretKeyRef: key: POSTGRES_DB name: feedbin-db - name: POSTGRESQL_PASSWORD valueFrom: secretKeyRef: key: POSTGRES_PASSWORD name: feedbin-db - name: POSTGRESQL_USER valueFrom: secretKeyRef: key: POSTGRES_USER name: feedbin-db volumeMounts: - name: feedbin-data mountPath: /var/lib/pgsql/data subPath: psql-data resources: limits: cpu: 150m memory: 100Mi - name: feedbin image: rocwhite/feedbin-aio imagePullPolicy: Always env: - name: NUM_UNICORN_WORKER value: "2" - name: discovery.type value: "single-node" - name: PUSH_URL value: 'http://feedbin.yourdomain.tls - name: SECRET_KEY_BASE valueFrom: secretKeyRef: key: SECRET_KEY_BASE name: feedbin-secrets - name: SKYLIGHT_AUTHENTICATION valueFrom: secretKeyRef: key: SKYLIGHT_AUTHENTICATION name: feedbin-secrets - name: STRIPE_API_KEY valueFrom: secretKeyRef: key: STRIPE_API_KEY name: feedbin-secrets - name: STRIPE_PUBLIC_KEY valueFrom: secretKeyRef: key: STRIPE_PUBLIC_KEY name: feedbin-secrets - name: POSTGRES_DB valueFrom: secretKeyRef: key: POSTGRES_DB name: feedbin-db - name: POSTGRES_PASSWORD valueFrom: secretKeyRef: key: POSTGRES_PASSWORD name: feedbin-db - name: POSTGRES_USER valueFrom: secretKeyRef: key: POSTGRES_USER name: feedbin-db resources: limits: cpu: 1350m memory: 770Mi volumeMounts: - name: feedbin-data mountPath: /usr/share/elasticsearch/data subPath: es-data volumes: - name: feedbin-data persistentVolumeClaim: claimName: data restartPolicy: Always test: false triggers: - type: ConfigChange - imageChangeParams: automatic: true containerNames: - feedbin from: kind: ImageStreamTag name: feedbin:latest # namespace: type: ImageChange - apiVersion: v1 kind: Service metadata: name: feedbin spec: ports: - name: web port: 8080 protocol: TCP targetPort: 3000 selector: name: feedbin sessionAffinity: None type: ClusterIP - apiVersion: v1 kind: Route metadata: name: feedbin spec: host: port: targetPort: web tls: insecureEdgeTerminationPolicy: Redirect termination: edge to: kind: Service name: feedbin weight: 100 wildcardPolicy: None
Comments
Comments powered by Disqus