Passed
Push — master ( 86dc00...a7425d )
by Tomasz
03:14
created

Device_Linux::checkNMResultAndCont()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 17
Code Lines 10

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 1
eloc 10
nc 1
nop 0
dl 0
loc 17
rs 9.4285
c 0
b 0
f 0
1
<?php
2
3
/* * ********************************************************************************
4
 * (c) 2011-15 GÉANT on behalf of the GN3, GN3plus and GN4 consortia
5
 * License: see the LICENSE file in the root directory
6
 * ********************************************************************************* */
7
8
/**
9
 * This file creates Linux installers
10
 *
11
 * @author Tomasz Wolniewicz <[email protected]>
12
 * @author Michał Gasewicz <[email protected]> (Network Manager support)
13
 *
14
 * @package ModuleWriting
15
 */
16
namespace devices\linux;
17
/**
18
 * This class creates Linux installers. It supports NetworkManager and raw
19
 * wpa_supplicant files.
20
 *
21
 * @author Tomasz Wolniewicz <[email protected]>
22
 * @author Michał Gasewicz <[email protected]> (Network Manager support)
23
 *
24
 * @package ModuleWriting
25
 */
26
class Device_Linux extends \core\DeviceConfig {
27
28
    final public function __construct() {
29
        parent::__construct();
30
        $this->setSupportedEapMethods([\core\common\EAP::EAPTYPE_PEAP_MSCHAP2, \core\common\EAP::EAPTYPE_TTLS_PAP, \core\common\EAP::EAPTYPE_TTLS_MSCHAP2, \core\common\EAP::EAPTYPE_TLS, \core\common\EAP::EAPTYPE_SILVERBULLET]);
31
    }
32
33
    public function writeInstaller() {
34
        $installerPath = $this->installerBasename . ".py";
35
        $this->copyFile("main.py", $installerPath);
36
        $installer = fopen($installerPath,"a");
37
        fwrite($installer,$this->writeMessages());
38
        fwrite($installer,$this->writeConfigVars());
39
        fwrite($installer, "run_installer()\n");
40
        return($installerPath);
41
    }
42
43
    public function writeDeviceInfo() {
44
        $ssidCount = count($this->attributes['internal:SSID']);
45
        $out = '';
46
47
        $out .= _("The installer is in the form of a bash script. It will try to configure eduroam under Network Manager and if this is either not appropriate for your system or your version of Network Manager is too old, a wpa_supplicant config file will be created instead.");
48
        $out .= "<p>";
49
        if ($ssidCount > 1) {
50
            if ($ssidCount > 2) {
51
                $out .= sprintf(_("In addition to <strong>%s</strong> the installer will also configure access to the following networks:"), implode(', ', CONFIG_CONFASSISTANT['CONSORTIUM']['ssid'])) . " ";
52
            } else {
53
                $out .= sprintf(_("In addition to <strong>%s</strong> the installer will also configure access to:"), implode(', ', CONFIG_CONFASSISTANT['CONSORTIUM']['ssid'])) . " ";
54
            }
55
            $iterator = 0;
56
            foreach ($this->attributes['internal:SSID'] as $ssid => $v) {
57
                if (!in_array($ssid, CONFIG_CONFASSISTANT['CONSORTIUM']['ssid'])) {
58
                    if ($iterator > 0) {
59
                        $out .= ", ";
60
                    }
61
                    $iterator++;
62
                    $out .= "<strong>$ssid</strong>";
63
                }
64
            }
65
            $out .= "<p>";
66
        }
67
        $out .= _("The installer will create .cat_installer sub-directory in your home directory and will copy your server certificates there.");
68
        if ($this->selectedEap == \core\common\EAP::EAPTYPE_TLS) {
69
            $out .= sprintf(_("In order to connect to the network you will need a personal certificate in the form of a p12 file. You should obtain this certificate from your %s. Consult the support page to find out how this certificate can be obtained. Such certificate files are password protected. You should have both the file and the password available during the installation process. Your p12 file will also be copied to the .cat_installer directory."), $this->nomenclature_inst);
70
        } elseif ($this->selectedEap != \core\common\EAP::EAPTYPE_SILVERBULLET) {
71
            $out .= sprintf(_("In order to connect to the network you will need an account from your %s. You should consult the support page to find out how this account can be obtained. It is very likely that your account is already activated."), $this->nomenclature_inst);
72
            $out .= "<p>";
73
            $out .= _("You will be requested to enter your account credentials during the installation. This information will be saved so that you will reconnect to the network automatically each time you are in the range.");
74
        }
75
        // nothing to say if we are doing silverbullet.
76
        $out .= "<p>";
77
        return $out;
78
    }
79
    
80
    private function writeMessages() {
81
        $out = '';
82
        $out .= 'Messages.quit = "' . _("Really quit?") . "\"\n";
83
        $out .= 'Messages.username_prompt = "' . _("enter your userid") . "\"\n";
84
        $out .= 'Messages.enter_password = "' . _("enter password") . "\"\n";
85
        $out .= 'Messages.enter_import_password = "' . _("enter your import password") . "\"\n";
86
        $out .= 'Messages.incorrect_password = "' . _("incorrect password") . "\"\n";
87
        $out .= 'Messages.repeat_password = "' . _("repeat your password") . "\"\n";
88
        $out .= 'Messages.passwords_difffer = "' . _("passwords do not match") . "\"\n";
89
        $out .= 'Messages.installation_finished = "' . _("Installation successful") . "\"\n";
90
        $out .= 'Messages.cat_dir_exisits = "' . _("Directory {} exists; some of its files may be overwritten.") . "\"\n";
91
        $out .= 'Messages.cont = "' . _("Continue?") . "\"\n";
92
        $out .= 'Messages.nm_not_supported = "' . _("This Network Manager version is not supported") . "\"\n";
93
        $out .= 'Messages.cert_error = "' . _("Certificate file not found, looks like a CAT error") . "\"\n";
94
        $out .= 'Messages.unknown_version = "' . _("Unknown version") . "\"\n";
95
        $out .= 'Messages.dbus_error = "' . _("DBus connection problem, a sudo might help") . "\"\n";
96
        $out .= 'Messages.yes = "' . _("Y") . "\"\n";
97
        $out .= 'Messages.no = "' . _("N") . "\"\n";
98
        $out .= 'Messages.p12_filter = "' . _("personal certificate file (p12 or pfx)") . "\"\n";
99
        $out .= 'Messages.all_filter = "' . _("All files") . "\"\n";
100
        $out .= 'Messages.p12_title = "' . _("personal certificate file (p12 or pfx)") . "\"\n";
101
        $out .= 'Messages.save_wpa_conf = "' . _("Network Manager configuration failed, but we may generate a wpa_supplicant configuration file if you wish. Be warned that your connection password will be saved in this file as clear text.") . "\"\n";
102
        $out .= 'Messages.save_wpa_confirm = "' . _("Write the file") . "\"\n";
103
        $out .= 'Messages.wrongUsernameFormat = "' ._("Error: Your username must be of the form 'xxx@institutionID' e.g. '[email protected]'!") . "\"\n";
104
        $out .= 'Messages.wrong_realm = "' . _("Error: your username must be in the form of 'xxx@{}'. Please enter the username in the correct format.") . "\"\n";
105
        $out .= 'Messages.wrong_realm_suffix = "' . _("Error: your username must be in the form of 'xxx@institutionID' and end with '{}'. Please enter the username in the correct format.") . "\"\n";
106
    
107
        return $out;
108
    }
109
    
110
    private function writeConfigVars() {
111
        $eapMethod = \core\common\EAP::eapDisplayName($this->selectedEap);
112
        $out = '';
113
        $out .= 'Config.instname = "' . $this->attributes['general:instname'][0] . '"' . "\n";
114
        $out .= 'Config.profilename = "' . $this->attributes['profile:name'][0] . '"' . "\n";
115
        $contacts = $this->mkSupportContacts();
116
        $out .= 'Config.url = "' . $contacts['url'] . '"' . "\n";
117
        $out .= 'Config.email = "' . $contacts['email'] . '"' . "\n";
118
        $out .= 'Config.title = "' . "eduroam CAT" . "\"\n";
119
        $out .= 'Config.servers = ' . $this->mkSubjectAltNameList() . "\n";
120
        $out .= 'Config.ssids = ' . $this->mkSsidList() . "\n";
121
        $out .= 'Config.del_ssids = ' . $this->mkDelSsidList() . "\n";
122
        $out .= "Config.server_match = '" . $this->glueServerNames() . "'\n";
123
        $out .= "Config.eap_outer = '" . $eapMethod['OUTER'] . "'\n";
124
        $out .= "Config.eap_inner = '" . $eapMethod['INNER'] . "'\n";
125
        if ($this->selectedEap == \core\common\EAP::EAPTYPE_TLS && isset($this->attributes['eap-specific:tls_use_other_id']) && $this->attributes['eap-specific:tls_use_other_id'][0] == 'on') {
126
            $out .= "Config.use_other_tls_id = True\n";
127
        }
128
        else {
129
            $out .= "Config.use_other_tls_id = False\n";
130
        }
131
        $tou = $this->mkUserConsent();
132
        $out .= 'Config.tou = ' . ( $tou ? '"""' . $tou . '"""' : 'None' ) . "\n"; 
133
        $out .= 'Config.CA = """' . $this->mkCAfile()  . '"""' . "\n";
134
        $out .= "Config.anonymous_identity = '" . $this->determineOuterIdString() . "'\n";
135
        $out .= 'Config.init_info = """' . $this->mkIntro() . '"""' . "\n";
136
        $out .= 'Config.init_confirmation = "' . $this->mkProfileConfirmation() . "\"\n";
137
        
138
        $out .= 'Config.sb_user_file = """' . $this->mkSbUserFile() . '"""' . "\n";
139 View Code Duplication
        if (!empty($this->attributes['internal:realm'][0])) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
140
           $out .= 'Config.user_realm = "' . $this->attributes['internal:realm'][0] . "\"\n";
141
        }
142 View Code Duplication
        if(!empty($this->attributes['internal:hint_userinput_suffix'][0]) && $this->attributes['internal:hint_userinput_suffix'][0] == 1) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
143
            $out .= "Config.hint_user_input = True\n";
144
        }
145 View Code Duplication
        if(!empty($this->attributes['internal:verify_userinput_suffix'][0]) && $this->attributes['internal:verify_userinput_suffix'][0] == 1) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
146
            $out .= "Config.verify_user_realm_input = True\n";
147
        }        
148
        return $out;
149
    }
150
151
    
152
    private function glueServerNames() {
153
        $serverList = $this->attributes['eap:server_name'];        
154
        if (!$serverList) {
155
            return '';
156
        }
157
        $A0 = array_reverse(explode('.', array_shift($serverList)));
158
        $B = $A0;
159
        foreach ($serverList as $oneServer) {
160
            $A = array_reverse(explode('.', $oneServer));
161
            $B = array_intersect_assoc($A0, $A);
162
            $A0 = $B;
163
        }
164
        return(implode('.', array_reverse($B)));
165
    }
166
167
    private function mkSupportContacts() {
168
        $url = (!empty($this->attributes['support:url'][0])) ? $this->attributes['support:url'][0] : $this->support_url_substitute;
169
        $email = (!empty($this->attributes['support:email'][0])) ? $this->attributes['support:email'][0] : $this->support_email_substitute;
170
        return(['url'=>$url, 'email'=>$email]);
171
    }   
172
    
173
    private function mkSubjectAltNameList() {
174
        $serverList = $this->attributes['eap:server_name'];
175
        if (!$serverList) {
176
            return '';
177
        }
178
        $out = '';
179
        foreach ($serverList as $oneServer) {
180
            if ($out) {
181
                $out .= ',';
182
            }
183
            $out .= "'DNS:$oneServer'";
184
        }
185
        return "[" . $out. "]";
186
    }
187
188
    
189 View Code Duplication
    private function mkSsidList() {
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
190
        $ssids = $this->attributes['internal:SSID'];
191
        $outArray = [];
192
        foreach ($ssids as $ssid => $cipher) {
193
            $outArray[] = "'$ssid'";
194
        }
195
        return '[' . implode(', ', $outArray) . ']';
196
    }
197
    
198 View Code Duplication
    private function mkDelSsidList() {
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
199
        $outArray = [];
200
        $delSSIDs = $this->attributes['internal:remove_SSID'];
201
        foreach ($delSSIDs as $ssid => $cipher) {
202
            if ($cipher == 'DEL') {
203
                $outArray[] = "'$ssid'";
204
            }
205
        }
206
        return '[' . implode(', ', $outArray) . ']';
207
    }
208
    
209
    private function mkCAfile(){
210
        $out = '';
211
        $cAlist = $this->attributes['internal:CAs'][0];
212
        foreach ($cAlist as $oneCa) {
213
            $out .= $oneCa['pem'] . "\n";
214
        }
215
        return $out;
216
    }
217
    
218
    private function mkIntro() {
219
        $out = _("This installer has been prepared for {0}") . '\n\n' . _("More information and comments:") . '\n\nEMAIL: {1}\nWWW: {2}\n\n' .
220
            _("Installer created with software from the GEANT project.") . "\"\n";
221
        return $out;
222
    }
223
    
224
    private function mkUserConsent() {
225
        $out = '';
226
        if (isset($this->attributes['support:info_file'])) {
227
            if ($this->attributes['internal:info_file'][0]['mime'] == 'txt') {
228
                $out = $this->attributes['support:info_file'][0];
229
            }
230
        }
231
        return $out;
232
    }
233
    
234
    private function mkProfileConfirmation() {
235
        if ($this->attributes['internal:profile_count'][0] > 1) {
236
            $out = _("This installer will only work properly if you are a member of {0} and the user group: {1}.");
237
        } else {
238
            $out = _("This installer will only work properly if you are a member of {0}.");
239
        }
240
        return $out;
241
    }
242
    
243
244
    
245
    private function mkSbUserFile() {
246
        if ($this->selectedEap == \core\common\EAP::EAPTYPE_SILVERBULLET) {
247
            return chunk_split(base64_encode($this->clientCert["certdata"]), 64, "\n");
248
        }
249
        return "";
250
    }
251
    
252
}
253