Exemple #1
0
RAISES_NEG int
conn_set_client_encoding(connectionObject *self, const char *pgenc)
{
    PGresult *pgres = NULL;
    char *error = NULL;
    int res = -1;
    char *clean_enc = NULL;

    /* We must know what python encoding this encoding is. */
    if (0 > clear_encoding_name(pgenc, &clean_enc)) { goto exit; }

    /* If the current encoding is equal to the requested one we don't
       issue any query to the backend */
    if (strcmp(self->encoding, clean_enc) == 0) return 0;

    Py_BEGIN_ALLOW_THREADS;
    pthread_mutex_lock(&self->lock);

    /* abort the current transaction, to set the encoding ouside of
       transactions */
    if ((res = pq_abort_locked(self, &pgres, &error, &_save))) {
        goto endlock;
    }

    if ((res = pq_set_guc_locked(self, "client_encoding", clean_enc,
            &pgres, &error, &_save))) {
        goto endlock;
    }

endlock:
    pthread_mutex_unlock(&self->lock);
    Py_END_ALLOW_THREADS;

    if (res < 0) {
        pq_complete_error(self, &pgres, &error);
        goto exit;
    }

    res = conn_store_encoding(self, pgenc);

    Dprintf("conn_set_client_encoding: encoding set to %s", self->encoding);

exit:
    PyMem_Free(clean_enc);

    return res;
}
/* Read the client encoding from the connection.
 *
 * Store the encoding in the pgconn->encoding field and the name of the
 * matching python codec in codec. The buffers are allocated on the Python
 * heap.
 *
 * Return 0 on success, else nonzero.
 */
RAISES_NEG static int
conn_read_encoding(connectionObject *self, PGconn *pgconn)
{
    char *enc = NULL, *codec = NULL;
    const char *tmp;
    int rv = -1;

    tmp = PQparameterStatus(pgconn, "client_encoding");
    Dprintf("conn_connect: client encoding: %s", tmp ? tmp : "(none)");
    if (!tmp) {
        PyErr_SetString(OperationalError,
            "server didn't return client encoding");
        goto exit;
    }

    if (0 > clear_encoding_name(tmp, &enc)) {
        goto exit;
    }

    /* Look for this encoding in Python codecs. */
    if (0 > conn_encoding_to_codec(enc, &codec)) {
        goto exit;
    }

    /* Good, success: store the encoding/codec in the connection. */
    PyMem_Free(self->encoding);
    self->encoding = enc;
    enc = NULL;

    PyMem_Free(self->codec);
    self->codec = codec;
    codec = NULL;

    rv = 0;

exit:
    PyMem_Free(enc);
    PyMem_Free(codec);
    return rv;
}
Exemple #3
0
/* Return the Python encoding from a PostgreSQL encoding.
 *
 * Optionally return the clean version of the postgres encoding too
 */
PyObject *
conn_pgenc_to_pyenc(const char *encoding, char **clean_encoding)
{
    char *pgenc = NULL;
    PyObject *rv = NULL;

    if (0 > clear_encoding_name(encoding, &pgenc)) { goto exit; }
    if (!(rv = PyDict_GetItemString(psycoEncodings, pgenc))) {
        PyErr_Format(OperationalError,
            "no Python encoding for PostgreSQL encoding '%s'", pgenc);
        goto exit;
    }
    Py_INCREF(rv);

    if (clean_encoding) {
        *clean_encoding = pgenc;
    }
    else {
        PyMem_Free(pgenc);
    }

exit:
    return rv;
}
RAISES_NEG int
conn_set_client_encoding(connectionObject *self, const char *enc)
{
    PGresult *pgres = NULL;
    char *error = NULL;
    int res = -1;
    char *codec = NULL;
    char *clean_enc = NULL;

    /* If the current encoding is equal to the requested one we don't
       issue any query to the backend */
    if (strcmp(self->encoding, enc) == 0) return 0;

    /* We must know what python codec this encoding is. */
    if (0 > clear_encoding_name(enc, &clean_enc)) { goto exit; }
    if (0 > conn_encoding_to_codec(clean_enc, &codec)) { goto exit; }

    Py_BEGIN_ALLOW_THREADS;
    pthread_mutex_lock(&self->lock);

    /* abort the current transaction, to set the encoding ouside of
       transactions */
    if ((res = pq_abort_locked(self, &pgres, &error, &_save))) {
        goto endlock;
    }

    if ((res = pq_set_guc_locked(self, "client_encoding", clean_enc,
            &pgres, &error, &_save))) {
        goto endlock;
    }

    /* no error, we can proceed and store the new encoding */
    {
        char *tmp = self->encoding;
        self->encoding = clean_enc;
        PyMem_Free(tmp);
        clean_enc = NULL;
    }

    /* Store the python codec too. */
    {
        char *tmp = self->codec;
        self->codec = codec;
        PyMem_Free(tmp);
        codec = NULL;
    }

    Dprintf("conn_set_client_encoding: set encoding to %s (codec: %s)",
            self->encoding, self->codec);

endlock:
    pthread_mutex_unlock(&self->lock);
    Py_END_ALLOW_THREADS;

    if (res < 0)
        pq_complete_error(self, &pgres, &error);

exit:
    PyMem_Free(clean_enc);
    PyMem_Free(codec);

    return res;
}