R
Railway•13mo ago
stkr

Weasyprint: OSError: cannot load library 'gobject-2.0-0' while trying to deploy Django project

Hi everyone, I'm a student in software development and new to Django and Railway. Me and my friends we have build a little app in Django and that app uses weasyprint to generate a pdf report file. We decided to deploy on Railway. Unfortunately, the deployement crashes and we'are getting that error log:
from . import views File "/app/DepistClic/mainapp/views.py", line 6, in <module> from weasyprint import HTML, CSS ...
File "/opt/venv/lib/python3.10/site-packages/cffi/api.py", line 832, in _make_ffi_library backendlib = _load_backend_lib(backend, libname, flags) File "/opt/venv/lib/python3.10/site-packages/cffi/api.py", line 827, in _load_backend_lib raise OSError(msg) OSError: cannot load library 'gobject-2.0-0': gobject-2.0-0: cannot open shared object file: No such file or directory. Additionally, ctypes.util.find_library() did not manage to locate a library called 'gobject-2.0-0'
I have spent hours searching a solution. I understand that some additional packages are needed as said in that documentation https://doc.courtbouillon.org/weasyprint/stable/first_steps.html#ubuntu-20-04 So I tried to add them in a nixpacks.toml file at the root of my project: [phases.setup] aptPkgs = ["...", "python3-pip", "python3-cffi", "python3-brotli", "libpango-1.0-0", "libharfbuzz0b", "libpangoft2-1.0-0"]
And nixpacks seems to setup these packages (see the image). But I still got hte error "OSError: cannot load library 'gobject-2.0-0': gobject-2.0-0: cannot open shared object file: No such file or directory. Additionally, ctypes.util.find_library() did not manage to locate a library called 'gobject-2.0-0'"
And deployement inevitably crashes. I would really appreciate if anyone could help us to resolve this issue. I feel that I'm close to the solution but I miss something. Thanks a lot !
No description
Solution:
Thanks a lot for your response. I really appreciate that ! While waiting, I've read posts from people with the same problem and after multiples attempts I managed to resolve the issue with this dockerfile: `FROM python:3.10.12 RUN apt-get update RUN apt-get -y install python3-pip python3-cffi python3-brotli libpango-1.0-0 libpangoft2-1.0-0...
Jump to solution
11 Replies
Percy
Percy•13mo ago
Project ID: d616bd58-0440-4197-b741-24b36e54d293
stkr
stkrOP•13mo ago
Project ID: d616bd58-0440-4197-b741-24b36e54d293
pandas
pandas•13mo ago
Hey man, Here's setup with weasyprint and flask, should work just fine on django Dockerfile
# Use an official Python runtime as a parent image
FROM python:3.8

# Set the working directory in the container
WORKDIR /usr/src/app

# Install WeasyPrint dependencies
RUN apt-get update \
&& apt-get install -y --no-install-recommends \
build-essential \
python3-dev \
python3-pip \
python3-setuptools \
python3-wheel \
python3-cffi \
libcairo2 \
libpango-1.0-0 \
libpangocairo-1.0-0 \
libgdk-pixbuf2.0-0 \
libffi-dev \
shared-mime-info \
&& apt-get clean \
&& rm -rf /var/lib/apt/lists/*

# Install Python dependencies
COPY requirements.txt ./
RUN pip install --no-cache-dir -r requirements.txt

# Copy the current directory contents into the container at /usr/src/app
COPY . .

# Make port 8081 available to the world outside this container
EXPOSE 8081

# Run app.py when the container launches
CMD ["gunicorn", "main:app"]
# Use an official Python runtime as a parent image
FROM python:3.8

# Set the working directory in the container
WORKDIR /usr/src/app

# Install WeasyPrint dependencies
RUN apt-get update \
&& apt-get install -y --no-install-recommends \
build-essential \
python3-dev \
python3-pip \
python3-setuptools \
python3-wheel \
python3-cffi \
libcairo2 \
libpango-1.0-0 \
libpangocairo-1.0-0 \
libgdk-pixbuf2.0-0 \
libffi-dev \
shared-mime-info \
&& apt-get clean \
&& rm -rf /var/lib/apt/lists/*

# Install Python dependencies
COPY requirements.txt ./
RUN pip install --no-cache-dir -r requirements.txt

# Copy the current directory contents into the container at /usr/src/app
COPY . .

# Make port 8081 available to the world outside this container
EXPOSE 8081

# Run app.py when the container launches
CMD ["gunicorn", "main:app"]
requirements.txt
Flask
boto3
weasyprint
gunicorn
Flask
boto3
weasyprint
gunicorn
main.py
from flask import Flask, request, jsonify
from weasyprint import HTML
import boto3
from botocore.exceptions import NoCredentialsError
import io
import uuid

app = Flask(__name__)

@app.route('/', methods=['GET'])
def hello():
return jsonify({"hello": "back"}), 200

@app.route('/generate-pdf', methods=['POST'])
def generate_pdf():
html_content = request.data.decode('utf-8')
if not html_content:
return jsonify({"error": "No HTML content provided"}), 400

# Convert HTML to PDF using WeasyPrint
try:
pdf = HTML(string=html_content).write_pdf()
except Exception as e:
return jsonify({"error": str(e)}), 500

# Upload to DigitalOcean Spaces
try:
session = boto3.session.Session()
client = session.client('s3',
region_name='region',
endpoint_url='https://bucket.digitaloceanspaces.com',
aws_access_key_id='key_id',
aws_secret_access_key='access_key'
)
file_name = f'{uuid.uuid4()}.pdf'
client.put_object(Bucket='bucket', # Replace with your bucket name
Key=file_name,
Body=io.BytesIO(pdf),
ACL='public-read')

return jsonify({
"message": "PDF uploaded successfully",
"file": file_name,
"url": f'https://bucket.region.digitaloceanspaces.com/{file_name}',
}), 200
except NoCredentialsError:
return jsonify({"error": "Credentials not available"}), 401
except Exception as e:
return jsonify({"error": str(e)}), 500


if __name__ == '__main__':
app.run(debug=True, host='0.0.0.0', port=os.getenv("PORT", default=8081))
from flask import Flask, request, jsonify
from weasyprint import HTML
import boto3
from botocore.exceptions import NoCredentialsError
import io
import uuid

app = Flask(__name__)

@app.route('/', methods=['GET'])
def hello():
return jsonify({"hello": "back"}), 200

@app.route('/generate-pdf', methods=['POST'])
def generate_pdf():
html_content = request.data.decode('utf-8')
if not html_content:
return jsonify({"error": "No HTML content provided"}), 400

# Convert HTML to PDF using WeasyPrint
try:
pdf = HTML(string=html_content).write_pdf()
except Exception as e:
return jsonify({"error": str(e)}), 500

# Upload to DigitalOcean Spaces
try:
session = boto3.session.Session()
client = session.client('s3',
region_name='region',
endpoint_url='https://bucket.digitaloceanspaces.com',
aws_access_key_id='key_id',
aws_secret_access_key='access_key'
)
file_name = f'{uuid.uuid4()}.pdf'
client.put_object(Bucket='bucket', # Replace with your bucket name
Key=file_name,
Body=io.BytesIO(pdf),
ACL='public-read')

return jsonify({
"message": "PDF uploaded successfully",
"file": file_name,
"url": f'https://bucket.region.digitaloceanspaces.com/{file_name}',
}), 200
except NoCredentialsError:
return jsonify({"error": "Credentials not available"}), 401
except Exception as e:
return jsonify({"error": str(e)}), 500


if __name__ == '__main__':
app.run(debug=True, host='0.0.0.0', port=os.getenv("PORT", default=8081))
pandas
pandas•13mo ago
project structure
No description
pandas
pandas•13mo ago
This setup works out of the box deploying on railways, just add domain boto3 can be changed to anything you prefer to use as a file serving to user
Solution
stkr
stkr•13mo ago
Thanks a lot for your response. I really appreciate that ! While waiting, I've read posts from people with the same problem and after multiples attempts I managed to resolve the issue with this dockerfile: FROM python:3.10.12 RUN apt-get update RUN apt-get -y install python3-pip python3-cffi python3-brotli libpango-1.0-0 libpangoft2-1.0-0 WORKDIR /app RUN pip install pipenv COPY Pipfile Pipfile.lock ./ RUN pipenv install --deploy --ignore-pipfile COPY . ./ CMD pipenv run python DepistClic/manage.py migrate && pipenv run python DepistClic/manage.py collectstatic --no-input && pipenv run gunicorn locallibrary.wsgi
stkr
stkrOP•13mo ago
Thanks a lot for your help again
pandas
pandas•13mo ago
Awesome! Nice find, yeah docker is a lot easier to manage and more flexible
stkr
stkrOP•13mo ago
I'm still on the deployement, I hope that this issue will not surface again. Just one question, I do not master Docker so I'm learning on the road. Is it mandatory to add "EXPOSE 8081" or "EXPOSE 8000" to the dockerfile ? Everyone who resolved the weasyprint issue seem to have used the dockerfile with these settings
pandas
pandas•13mo ago
Not mandatory, but a good practice for future development If you still have issues with Dockerfile you sent try one I sent, tested it 5 minutes ago works great 😅 Just one key thing
port=os.getenv("PORT", default=8081)
port=os.getenv("PORT", default=8081)
Let application discover port that has been set by railway you can also override that setting https://docs.railway.app/deploy/exposing-your-app
stkr
stkrOP•13mo ago
Thanks a lot for your help ! I will do that
Want results from more Discord servers?
Add your server