Completed
Push — master ( 1af4f5...caaac4 )
by Andreas
03:43
created

connection   A

Complexity

Total Complexity 24

Size/Duplication

Total Lines 207
Duplicated Lines 0 %

Coupling/Cohesion

Components 1
Dependencies 15

Test Coverage

Coverage 80%

Importance

Changes 0
Metric Value
dl 0
loc 207
ccs 72
cts 90
cp 0.8
rs 9.1666
c 0
b 0
f 0
wmc 24
lcom 1
cbo 15

10 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 4 1
A get_em() 0 7 2
A get_user() 0 4 1
A set_user() 0 7 2
A generate_guid() 0 5 1
A set_autostart() 0 4 1
A initialize() 0 20 2
A get_parameter() 0 7 2
C startup() 0 49 7
B log() 0 18 5
1
<?php
2
/**
3
 * @author CONTENT CONTROL http://www.contentcontrol-berlin.de/
4
 * @copyright CONTENT CONTROL http://www.contentcontrol-berlin.de/
5
 * @license http://www.gnu.org/licenses/gpl.html GNU General Public License
6
 */
7
8
namespace midgard\portable\storage;
9
10
use midgard\portable\driver;
11
use midgard\portable\classgenerator;
12
use midgard\portable\api\user;
13
use midgard\portable\api\config;
14
use midgard\portable\api\error\exception;
15
use midgard\portable\storage\type\datetime;
16
use Doctrine\ORM\EntityManagerInterface;
17
use Doctrine\DBAL\Types\Type;
18
use Monolog\Logger;
19
use Monolog\Handler\StreamHandler;
20
use midgard_connection;
21
22
class connection
23
{
24
    /**
25
     * @var Logger
26
     */
27
    private static $logger;
28
29
    /**
30
     * Loglevel translation table.
31
     *
32
     * The semantics of info and notice/message are unfortunately reversed between Monolog
33
     * and Midgard, so it looks a bit confusing..
34
     *
35
     * @var array
36
     */
37
    private static $loglevels = array(
38
        'error' => Logger::ERROR,
39
        'warn' => Logger::WARNING,
40
        'warning' => Logger::WARNING,
41
        'info' => Logger::NOTICE,
42
        'message' => Logger::INFO,
43
        'debug' => Logger::DEBUG
44
    );
45
46
    /**
47
     * Flag for automatically starting up during initialize
48
     *
49
     * @var boolean
50
     */
51
    private static $autostart = true;
52
53
    /**
54
     * Initialization parameters
55
     *
56
     * @param array
57
     */
58
    private static $parameters = array();
59
60
    private $user;
61
62
    /**
63
     * @var \Doctrine\ORM\EntityManagerInterface
64
     */
65
    protected $em;
66
67
    /**
68
     * @var \midgard\portable\storage\connection
69
     */
70
    protected static $instance;
71
72 10
    public function __construct(EntityManagerInterface $em)
73
    {
74 10
        $this->em = $em;
75 10
    }
76
77
    /**
78
     * @return \Doctrine\ORM\EntityManagerInterface
79
     */
80 147
    public static function get_em()
81
    {
82 147
        if (self::$instance === null) {
83
            throw new \Exception('Not initialized');
84
        }
85 147
        return self::$instance->em;
86
    }
87
88 96
    public static function get_user()
89
    {
90 96
        return self::$instance->user;
91
    }
92
93 8
    public static function set_user(user $user = null)
94
    {
95 8
        if (self::$instance === null) {
96
            throw new \Exception('Not initialized');
97
        }
98 8
        self::$instance->user = $user;
99 8
    }
100
101
    /**
102
     * Generate a new GUID
103
     *
104
     * @return string The generated GUID
105
     */
106 103
    public static function generate_guid()
107
    {
108 103
        $sql = 'SELECT ' . self::get_em()->getConnection()->getDatabasePlatform()->getGuidExpression();
109 103
        return md5(self::get_em()->getConnection()->query($sql)->fetchColumn(0));
110
    }
111
112
    /**
113
     * Toggle autostart
114
     */
115
    public static function set_autostart($autostart)
116
    {
117
        self::$autostart = $autostart;
118
    }
119
120
    /**
121
     * Initialize Midgard connection
122
     */
123 10
    public static function initialize(driver $driver, array $db_config, $dev_mode = false)
124
    {
125 10
        $vardir = $driver->get_vardir();
126
127 10
        $mgd_config = new config;
128 10
        $mgd_config->vardir = $vardir;
129 10
        $mgd_config->cachedir = $vardir . '/cache';
130 10
        $mgd_config->blobdir = $vardir . '/blobs';
131 10
        $mgd_config->sharedir = $vardir . '/schemas';
132 10
        $mgd_config->logfilename = $vardir . '/log/midgard-portable.log';
133
        // TODO: Set rest of config values from $config and $driver
134
135
        // we open the config before startup to have logfile available
136 10
        midgard_connection::get_instance()->open_config($mgd_config);
137
138 10
        self::$parameters = array('driver' => $driver, 'db_config' => $db_config, 'dev_mode' => $dev_mode);
139 10
        if (self::$autostart) {
140 10
            static::startup();
141 10
        }
142 10
    }
143
144
    public static function get_parameter($name)
145
    {
146
        if (!array_key_exists($name, self::$parameters)) {
147
            throw new \RuntimeException('Parameter "' . $name . '" is not available');
148
        }
149
        return self::$parameters[$name];
150
    }
151
152
    /**
153
     * Start the API emulation layer
154
     */
155 10
    public static function startup()
156
    {
157 10
        if (empty(self::$parameters)) {
158
            throw new \RuntimeError('Not initialized');
159
        }
160 10
        $driver = self::$parameters['driver'];
161 10
        $db_config = self::$parameters['db_config'];
162 10
        $dev_mode = self::$parameters['dev_mode'];
163 10
        $vardir = $driver->get_vardir();
164
        // generate and include midgard_objects.php if its a fresh namespace
165
        // otherwise it should be included already
166 10
        if ($driver->is_fresh_namespace()) {
167 10
            $entityfile = $vardir . '/midgard_objects.php';
168 10
            if ($dev_mode) {
169 10
                $classgenerator = new classgenerator($driver->get_manager(), $entityfile, $dev_mode);
170 10
                $classgenerator->write($driver->get_namespace());
171 10
            }
172 10
            require $entityfile;
173 10
        }
174
175 10
        $config = \Doctrine\ORM\Tools\Setup::createConfiguration($dev_mode, $vardir . '/cache');
176 10
        $config->addFilter('softdelete', 'midgard\\portable\\storage\\filter\\softdelete');
177 10
        $config->setMetadataDriverImpl($driver);
178 10
        $config->addEntityNamespace('midgard', $driver->get_namespace());
179 10
        $config->setClassMetadataFactoryName('\\midgard\\portable\\mapping\\factory');
180
181 10
        if (!array_key_exists('charset', $db_config)) {
182 10
            $db_config['charset'] = 'utf8';
183 10
        }
184
185 10
        $em = \Doctrine\ORM\EntityManager::create($db_config, $config);
186 10
        $em->getFilters()->enable('softdelete');
187 10
        $em->getEventManager()->addEventSubscriber(new subscriber);
188
189 10
        if (!Type::hasType(datetime::TYPE)) {
190
            Type::addType(datetime::TYPE, 'midgard\portable\storage\type\datetime');
191
        }
192
193 10
        $midgard = midgard_connection::get_instance();
194 10
        $level = self::$loglevels[$midgard->get_loglevel()];
195 10
        if ($level === Logger::DEBUG) {
196
            $logger = new Logger('doctrine');
197
            $logger->pushHandler(new StreamHandler($midgard->config->logfilename, $level));
198
199
            $em->getConnection()->getConfiguration()->setSQLLogger(new sqllogger($logger));
200
        }
201
202 10
        self::$instance = new static($em);
203 10
    }
204
205
    /**
206
     * Get Logger instance
207
     *
208
     * @return Logger
209
     */
210 3
    public static function log()
211
    {
212 3
        if (self::$logger === null) {
213 1
            $midgard = midgard_connection::get_instance();
214 1
            if ($midgard->config->logfilename) {
215 1
                $logdir = dirname($midgard->config->logfilename);
216 1
                if (   !is_dir($logdir)
217 1
                    && !mkdir($logdir, 0777, true)) {
218
                    throw exception::user_data('Log directory could not be created');
219
                }
220 1
                self::$logger = new Logger('midgard-portable');
221 1
                self::$logger->pushHandler(new StreamHandler($midgard->config->logfilename, self::$loglevels[$midgard->get_loglevel()]));
222 1
            } else {
223
                throw exception::user_data('log filename not set in config');
224
            }
225 1
        }
226 3
        return self::$logger;
227
    }
228
}
229