<commit_before>/* engine.vala
 *
 * Copyright © 2011 Collabora Ltd.
 *             By <NAME> <<EMAIL>>
 *             By <NAME> <<EMAIL>>
 *
 * Based upon a Python implementation (2009-2011) by:
 *  <NAME> <<EMAIL>>
 *  <NAME> <<EMAIL>>
 *  <NAME> <<EMAIL>>
 *  <NAME> <<EMAIL>>
 *
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU Lesser General Public License as published by
 * the Free Software Foundation, either version 2.1 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 *
 */

using Zeitgeist;
using Zeitgeist.SQLite;

namespace Zeitgeist
{ // FIXME: increase indentation once we're ok with breaking 'bzr diff'

public class Engine : Object
{

    Zeitgeist.SQLite.ZeitgeistDatabase database;
    unowned Sqlite.Database db;

    TableLookup interpretations_table;
    TableLookup manifestations_table;
    TableLookup mimetypes_table;
    TableLookup actors_table;

    uint32 last_id;

    public Engine () throws EngineError
    {
        database = new Zeitgeist.SQLite.ZeitgeistDatabase();
        db = database.database;
        last_id = database.get_last_id();

        interpretations_table = new TableLookup(database, "interpretation");
        manifestations_table = new TableLookup(database, "manifestation");
        mimetypes_table = new TableLookup(database, "mimetype");
        actors_table = new TableLookup(database, "actor");

        // FIXME: load extensions
    }

    public GenericArray<Event?> get_events(uint32[] event_ids,
            BusName? sender=null) throws EngineError
    {
        // TODO: Consider if we still want the cache. This should be done
        //  once everything is working, since it adds unneeded complexity.
        //  It'd also benchmark it again first, we may have better options
        //  to enhance the performance of SQLite now, and event processing
        //  will be faster now being C.

        Sqlite.Statement stmt;
        int rc;

        var sql_event_ids = database.get_sql_string_from_event_ids (event_ids);
        string sql = """
            SELECT * FROM event_view
            WHERE id IN (%s)
            """.printf (sql_event_ids);

        rc = db.prepare_v2 (sql, -1, out stmt);
        database.assert_query_success(rc, "SQL error");

        var events = new HashTable<uint32, Event?>(direct_hash, direct_equal);
       
        while ((rc = stmt.step()) == Sqlite.ROW)
        {
            uint32 event_id = (uint32) stmt.column_int64 (EventViewRows.ID);
            Event event; 
            if (events.lookup(event_id)!= null)
                event = events.lookup(event_id);
            else
            {
                event = new Event ();
                event.id = event_id;
                event.timestamp = stmt.column_int64 (EventViewRows.TIMESTAMP);
                event.interpretation = interpretations_table.get_value (
                    stmt.column_int (EventViewRows.INTERPRETATION));
                event.manifestation = manifestations_table.get_value (
                    stmt.column_int (EventViewRows.MANIFESTATION));
                event.actor = actors_table.get_value (
                    stmt.column_int (EventViewRows.ACTOR));
                event.origin = stmt.column_text (
                    EventViewRows.EVENT_ORIGIN_URI);
                // FIXME: payload
                events.insert(event_id, event);
            }


            Subject subject = new Subject ();
            subject.uri = stmt.column_text (EventViewRows.SUBJECT_URI);
            subject.text = stmt.column_text (EventViewRows.SUBJECT_TEXT);
            subject.storage = stmt.column_text (EventViewRows.SUBJECT_STORAGE);
            subject.origin = stmt.column_text (EventViewRows.SUBJECT_ORIGIN_URI);
            subject.current_uri = stmt.column_text (
                EventViewRows.SUBJECT_CURRENT_URI);
            subject.interpretation = interpretations_table.get_value (
                stmt.column_int (EventViewRows.SUBJECT_INTERPRETATION));
            subject.manifestation = manifestations_table.get_value (
                stmt.column_int (EventViewRows.SUBJECT_MANIFESTATION));
            subject.mimetype = mimetypes_table.get_value (
                stmt.column_int (EventViewRows.SUBJECT_MIMETYPE));

            event.add_subject(subject);
        }
        if (rc != Sqlite.DONE)
        {
            warning ("Error: %d, %s\n", rc, db.errmsg ());
            // FIXME: throw some error??
        }
        
        /* //Print
        for (int i = 0; i < event_ids.length; ++i)
        {
            var event = events.lookup(i);
            if (event != null)
               event.debug_print ();
            else
                stdout.printf ("NULL_EVENT\n");
            stdout.printf ("\n");
        }*/

        var results = new GenericArray<Event?> ();
        foreach (var id in event_ids)
            results.add (events.lookup (id));
        return results;
    }
<commit_msg>FindEventIds: fix result array memory allocation, fix spacing issues.<commit_after>/* engine.vala
 *
 * Copyright © 2011 Collabora Ltd.
 *             By <NAME> <<EMAIL>>
 *             By <NAME> <<EMAIL>>
 *
 * Based upon a Python implementation (2009-2011) by:
 *  <NAME> <<EMAIL>>
 *  <NAME> <<EMAIL>>
 *  <NAME> <<EMAIL>>
 *  <NAME> <<EMAIL>>
 *
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU Lesser General Public License as published by
 * the Free Software Foundation, either version 2.1 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 *
 */

using Zeitgeist;
using Zeitgeist.SQLite;

namespace Zeitgeist
{ // FIXME: increase indentation once we're ok with breaking 'bzr diff'

public class Engine : Object
{

    Zeitgeist.SQLite.ZeitgeistDatabase database;
    unowned Sqlite.Database db;

    TableLookup interpretations_table;
    TableLookup manifestations_table;
    TableLookup mimetypes_table;
    TableLookup actors_table;

    uint32 last_id;

    public Engine () throws EngineError
    {
        database = new Zeitgeist.SQLite.ZeitgeistDatabase();
        db = database.database;
        last_id = database.get_last_id();

        interpretations_table = new TableLookup(database, "interpretation");
        manifestations_table = new TableLookup(database, "manifestation");
        mimetypes_table = new TableLookup(database, "mimetype");
        actors_table = new TableLookup(database, "actor");

        // FIXME: load extensions
    }

    public GenericArray<Event?> get_events(uint32[] event_ids,
            BusName? sender=null) throws EngineError
    {
        // TODO: Consider if we still want the cache. This should be done
        //  once everything is working, since it adds unneeded complexity.
        //  It'd also benchmark it again first, we may have better options
        //  to enhance the performance of SQLite now, and event processing
        //  will be faster now being C.

        Sqlite.Statement stmt;
        int rc;

        var sql_event_ids = database.get_sql_string_from_event_ids (event_ids);
        string sql = """
            SELECT * FROM event_view
            WHERE id IN (%s)
            """.printf (sql_event_ids);

        rc = db.prepare_v2 (sql, -1, out stmt);
        database.assert_query_success (rc, "SQL error");

        var events = new HashTable<uint32, Event?> (direct_hash, direct_equal);

        while ((rc = stmt.step ()) == Sqlite.ROW)
        {
            uint32 event_id = (uint32) stmt.column_int64 (EventViewRows.ID);
            Event event;
            if (events.lookup (event_id)!= null)
                event = events.lookup (event_id);
            else
            {
                event = new Event ();
                event.id = event_id;
                event.timestamp = stmt.column_int64 (EventViewRows.TIMESTAMP);
                event.interpretation = interpretations_table.get_value (
                    stmt.column_int (EventViewRows.INTERPRETATION));
                event.manifestation = manifestations_table.get_value (
                    stmt.column_int (EventViewRows.MANIFESTATION));
                event.actor = actors_table.get_value (
                    stmt.column_int (EventViewRows.ACTOR));
                event.origin = stmt.column_text (
                    EventViewRows.EVENT_ORIGIN_URI);
                // FIXME: payload
                events.insert (event_id, event);
            }


            Subject subject = new Subject ();
            subject.uri = stmt.column_text (EventViewRows.SUBJECT_URI);
            subject.text = stmt.column_text (EventViewRows.SUBJECT_TEXT);
            subject.storage = stmt.column_text (EventViewRows.SUBJECT_STORAGE);
            subject.origin = stmt.column_text (EventViewRows.SUBJECT_ORIGIN_URI);
            subject.current_uri = stmt.column_text (
                EventViewRows.SUBJECT_CURRENT_URI);
            subject.interpretation = interpretations_table.get_value (
                stmt.column_int (EventViewRows.SUBJECT_INTERPRETATION));
            subject.manifestation = manifestations_table.get_value (
                stmt.column_int (EventViewRows.SUBJECT_MANIFESTATION));
            subject.mimetype = mimetypes_table.get_value (
                stmt.column_int (EventViewRows.SUBJECT_MIMETYPE));

            event.add_subject(subject);
        }
        if (rc != Sqlite.DONE)
        {
            warning ("Error: %d, %s\n", rc, db.errmsg ());
            // FIXME: throw some error??
        }

        var results = new GenericArray<Event?> ();
        results.length = event_ids.length;
        foreach (var id in event_ids)
            results.add (events.lookup (id));
        return results;
    }

{'fraction_non_alphanumeric': 0.09171962439533339, 'fraction_numerical': 0.005785829460305416, 'mean_word_length': 2.226438188494492, 'pattern_counts': {'":': 0, '<': 48, '<?xml version=': 0, '>': 47, 'https://': 0, 'lorem ipsum': 0, 'www.': 2, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '756077', 'n_tokens_mistral': 2992, 'n_tokens_neox': 2846, 'n_words': 809}