summaryrefslogtreecommitdiffstats
path: root/index.php
blob: 3ca6749280ecb36ed6c0d7a4e769b01b5a0ccb3e (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
<?php
// OPOZORILA: PROGRAM MORA BITI NUJNO POD IMENOM index.php IN POGANJATI SE MORA POD Apache 2, ki podpria RewriteEngine, Imeti moraš SQL uporabnika in bazo,
// .htaccess mora delati, potrebno je imeti dovoljenja za pisanje v mapo. .htaccess ob prvem zagonu ne sme
// obstajati, naredi se sam. NUJNO MORATE SKOPIRATI MAPO securimage iz phpcaptcha.org/download/ zraven index.php, drugače captcha ne bo delala.
// (C) 2019 Anton Šijanec.
// Uporaba dovoljena za učenje in za nekomercijalne namene, brez zaslužkov in z navedbo avtorja. Hvala!
// exit("Balkan ŠortLink je v pripravi. Pripravljen bo čez okoli 2 dni. Anton Šijanec, Projekt začet 20. januarja, predviden čas začetka obratovanja storitve
// je 23. januar 2019. Program bo odprtokoden in dostopen na mojem GitHubu, AstiriL!");
session_start();
clearstatcache();
ini_set('display_errors', 'On');
error_reporting(E_ALL);
$nadaljuj = "ja";
include_once $_SERVER['DOCUMENT_ROOT'] . '/securimage/securimage.php';
$securimage = new Securimage();

$verzija = "0.0.19.01.21";
$log .= "Verzija: " . $verzija . "\n";


// definicije - uporabniškega vnosa ne preverjam, zato si ne naredite sql vrivanja (angl. sql injection) ali vrinjanja skript (ni htmlchars sanitizacije).
// drugače pa je program dokaj varen prej vrivanjem... upajmo... vsi ostali uporabniški vnosi so sanitizirani.
$servername = "lol.u.though.i.will.show.a4l.space"; // domena, IP naslov oziroma ime gostitelja za dostop do MySQL ali ekvivalentne SQL podatkovne baze (strežnika)
$username = "nofreesqlforyou"; // uporabniško ime za dostop do strežnika SQL
$password = "donttrytoconnect"; // geslo za dostop do strežnika SQL
$baza = "itdoesntwork"; // podatkovna baza SQL v katero naj pišem - naredi jo pred zagonom programa
$tabela = "srslyitdoesnt"; // tabela, ki naj jo naredim v podatkovni bazi SQL oziroma tabela v podatkovni bazi SQL, ki naj jo uporabljam
$rxshort = "/^[0-9a-z]{1,6}$/"; // angleško regular expression, ki naj ga uporabim za kratek niz - nujno popravi še besedilne opise. Pusti ga takega, kot je!
$domena = "š.ga"; // tvoja domena
$captcha = "ja"; // ja/ne: ali naj uporabljam captcho? potrebujete phpcaptcha.org, mapo securimage skopirajte zraven index.php (tega programa).

// samoinštalacija - .htaccess ne sme obstajati ob prvem zagonu
if(!file_exists(".htaccess")) {
	$htaccess = "
RewriteEngine on
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.*)$ /index.php?r=$1 [NC,L,QSA]
	";
	if(file_put_contents(".htaccess", $htaccess)) {
		exit("Program je bil verjetno zagnan prvič. Izdelava .htaccess je uspela.\n");
	} else {
		$log .= "Program je bil zagnan verjetno prvič. Izdelava .htaccess ni uspela. Popravi dovoljenja mape.\n";
	}
}
if($captcha !== "ne") {
if(!file_exists("securimage")) {
	exit("securimage mapa z datotekami za captcho ne obstaja. Naložite jo iz phpcaptcha.org/download in jo postavite zraven index.php, ali pa spremenite
	nastavitev captcha v konfiguracijah (definicije) iz ja na ne (ne priporočam).\n");
} else {
	// okejjjjj
}
}

// sql povezava in izbira podatkovne baze
$conn = mysqli_connect($servername, $username, $password, $baza); // naredi povezavo
if (!$conn) { // preveri povezavo
    die("<pre>Povezava v podatkovno bazo ni uspela. <!-- Razhroščevanje: " . mysqli_connect_error() . "-->\n</pre>");
} 
$log .= "Povezava v podatkovno bazo uspešna.\n";
if(mysqli_select_db($conn,$baza)) {
	$log .= "Izbira podatkovne baze uspešna.\n";
} else {
	die("Podatkovne baze ni bilo mogoče izbrati. <!-- Razhroščevanje: " . mysqli_error($conn) . "-->\n");
}





//poglej če tabela links obstaja
$alitabelaobstaja = mysqli_query($conn, 'SELECT 1 from `'.$tabela.'`');
if($alitabelaobstaja !== FALSE) {
   $log .= "Tabela v podatkovni bazi obstaja. Program je že bil v uporabi.\n";
} else {
   // ne - naredi jo!
   $log .= "Tabela v podatkovni bazi ne obstaja. Program je bil zagnan prvič. Poskusil jo bom narediti.\n";
$sql = "CREATE TABLE IF NOT EXISTS `".$tabela."` (
  `short` varchar(10) COLLATE utf8_unicode_ci NOT NULL,
  `long` text(767) COLLATE utf8_unicode_ci NOT NULL,
  PRIMARY KEY (`short`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci";
if (mysqli_query($conn, $sql)) {
    $log .= "Tabela v podatkovni bazi je bila uspešno narejena.\n";
} else {
    die("<pre>Napaka v izdelavi tabele v podatkovni bazi! <!-- razhroščevanje: " . mysqli_error($conn) . "-->\n</pre>");
}
}


//če je potrebna preusmeritev (glej .htaccess, pa ti bo jasno)
if(!empty($_REQUEST['r'])) {
	// preveri, če dolg niz že obstaja
$safer = mysqli_real_escape_string($conn, $_REQUEST['r']);
// echo $safer; //debug
$query = "SELECT `long` from `".$tabela."` where `short`='".$safer."';";
$result = mysqli_query($conn, $query);
echo mysqli_error($conn); //debug
if(mysqli_num_rows($result) > 0) {


	// echo array_pop(mysqli_fetch_row($result); //debug //to je to!
	$dolgkiobstaja = array_pop(mysqli_fetch_row($result)); //to je to!
	// ŠortLink obstaja, preusmerjam!
	header("Location: ".$dolgkiobstaja);
} else {
		 $log .= "Kratek URL še ne obstaja v podatkovni bazi.\n";
		  $alert .= "<div class=alert>
  <span class=closebtn onclick=this.parentElement.style.display='none';>&times;</span> 
<b>Napaka!</b> Kratek URL še ne obstaja v podatkovni bazi.
</div><br>";
}
}



// če je zahteva za vpis, vpiši!
if(!empty($_REQUEST['submit'])) {
	$log .= "Obrazec je bil izpolnjen, začenjam preverjanje vnosa.";
	
	
	
if($captcha !== "ne") {
	if ($securimage->check($_POST['captcha_code']) == false) {
		$log .= "Preverjanje človeštva (CAPTCHA) je negativno. Mogoče niste človek, zato ne bom nadaljeval.";
	$alert .= "<div class=alert>
  <span class=closebtn onclick=this.parentElement.style.display='none';>&times;</span> 
<b>Napaka preverjanja!</b> Preverjanje CAPTCHA je pokazalo negativni rezultat. Mogoče niste človek, zato ne bom nadaljeval.
</div><br>";
   $nadaljuj = "ne";
} else {
	$log .= "Preverjanje človeštva (CAPTCHA) je pozitivno. Človek ste.";
}
}

// regex match kratkega niza
if(preg_match($rxshort, $_REQUEST['short'])) {
	$log .= "Preverjanje krajšalnega niza je pozitivno. Krajševalni niz se lahko uporabi.\n";
} else {
	$log .= "Krajšalni niz se ne ujema z regexom " . $rxshort . ", zato ne bom nadaljeval.\n";
	$nadaljuj = "ne";
		$alert .= "<div class=alert>
  <span class=closebtn onclick=this.parentElement.style.display='none';>&times;</span> 
<b>Napaka vnosa!</b> Krajševalni niz se ne ujema z njegovimi pravili. Mora biti 1 do 6 znakov dolg in lahko vsebuje male črke in številke.
</div><br>";
}


// preverjanje, ce je res URL
if(filter_var($_REQUEST['long'], FILTER_VALIDATE_URL)) {
	$log .= "Preverjanje dolgega URL-ja je pozitivno. Dolg URL se lahko uporabi.\n";
} else {
	$log .= "Preverjanje dolgega URL-ja je negativno, zato ne bom nadeljeval.\n";
	$nadaljuj = "ne";
	$alert .= "<div class=alert>
  <span class=closebtn onclick=this.parentElement.style.display='none';>&times;</span> 
<b>Napaka vnosa!</b> Dolg URL se ne ujema z standardi. Poskusite ponovno.
</div><br>";
}


// preprecevanje sql prekoračitve
if(strlen($_REQUEST['long']) > 767) { //strlen pove bajte, mb_strlen pove dolžino niza
	$log .= "Dolg URL je predolg. Mora biti krajši od 767 bajtov, drugače lahko pride do napak v podatkovni bazi.\n";
	$nadaljuj = "ne";
	$alert .= "<div class=alert>
  <span class=closebtn onclick=this.parentElement.style.display='none';>&times;</span> 
<b>Napaka vnosa!</b> URL je predolg. Mora biti krajši od 767 bajtov.
</div><br>"; //drugače lahko pride do napak v SQL bazi podatkov
} else {
	$log .= "Dolg URL ni predolg. To je v redu.\n";
}

if($nadaljuj == "ja") { //nadaljuj z sql stvarmi, samo, če so zgornji pogoji zadostni

//preveri, če kratek niz že obstaja
$safeshort = mysqli_real_escape_string($conn, $_REQUEST['short']);
$query = "SELECT * from `".$tabela."` where `short`='".$safeshort."';";
$result = mysqli_query($conn, $query);
if(mysqli_num_rows($result) > 0) {
	 $alert .= "<div class=alert>
  <span class=closebtn onclick=this.parentElement.style.display='none';>&times;</span> 
<b>Napaka!</b> Krajšalni tekst že obstaja v podatkovni bazi. Izberite drugega.
</div><br>";
	 $log .= "Krajševalni tekst že obstaja v podatkovni bazi, zato ne morem nadaljevati.\n";
	 $nadaljuj = "ne";
} else {
		 $log .= "Krajševalni tekst še ne obstaja v podatkovni bazi. To je v redu.\n";
}

// preveri, če dolg niz že obstaja
$safelong = mysqli_real_escape_string($conn, $_REQUEST['long']);
$query = "SELECT `short` from `".$tabela."` where `long`='".$safelong."';";
$result = mysqli_query($conn, $query);
if(mysqli_num_rows($result) > 0) {
	// echo array_pop(mysqli_fetch_row($result); //debug //to je to!
	$kratekkiobstaja = array_pop(mysqli_fetch_row($result)); //to je to!
	 $alert .= "<div class=alert>
  <span class=closebtn onclick=this.parentElement.style.display='none';>&times;</span> 
<b>Napaka!</b> Dolg URL že obstaja v podatkovni bazi. Nanj kaže <b>".$domena."/".htmlspecialchars($kratekkiobstaja)."</b>
</div><br>";
	 $log .= "Dolg URL že obstaja v podatkovni bazi, zato ne morem nadaljevati.\n";
	 $nadaljuj = "ne";
} else {
		 $log .= "Dolg URL še ne obstaja v podatkovni bazi. To je v redu.\n";
}

	/*
//idk ne dela -- v redu, vem zakaj: podpičje manjka! jaoooo in še `'" jaooooo sql nima ", ' je za nize, ` je za stolpce, tabele,...
$prepared = mysqli_prepare($conn, "SELECT * FROM ".$tabela." WHERE short=?");
// var_dump(mysqli_error($conn)); //debug
$binded = mysqli_stmt_bind_param($prepared, "s", $_REQUEST['short']);
// echo $binded; //debug
$executed = mysqli_stmt_execute($prepared);
echo $executed; //debug
$binded_result = mysqli_stmt_bind_result($prepared, $rezultat);
echo $rezultat; //debug
$fetched = mysqli_stmt_fetch($prepared);
echo $fetched; //debug
$result = mysqli_query($conn, $prepared);
echo mysqli_error($conn); //debug
if(mysqli_num_rows($result) == 0) {
	 $log .= "Krajševalni tekst še ne obstaja v podatkovni bazi. To je v redu.\n";
} else {
	 $alert .= "<div class=alert>
  <span class=closebtn onclick=this.parentElement.style.display='none';>&times;</span> 
<b>Napaka!</b> Krajšalni tekst že obstaja v podatkovni bazi. Izberite drugega.
</div><br>";
	 $log .= "Krajševalni tekst že obstaja v podatkovni bazi, zato ne morem nadaljevati.\n";
	 $nadaljuj = "ne";
}

//preverjanje, če krajševalni niz že obstaja
$prepared = mysqli_prepare($conn, "SELECT * FROM ".$tabela." WHERE long=?");
// echo mysqli_error($conn); //debug
mysqli_stmt_bind_param($prepared, "s", $_REQUEST['long']);
$result = mysqli_query($conn);
if(mysqli_num_rows($result) == 0) {
	 $log .= "Dolg URL še ne obstaja v podatkovni bazi. To je v redu.\n";
} else {
	 $alert .= "<div class=alert>
  <span class=closebtn onclick=this.parentElement.style.display='none';>&times;</span> 
<b>Napaka!</b> Dolg URL že obstaja v podatkovni bazi. Nanj vodi <b>".$domena."/".htmlspecialchars($result)."</b>.
</div><br>";
	 $log .= "Dolg URL že obstaja v podatkovni bazi, zato ne morem nadaljevati. Nanj vodi ".$domena."/".htmlspecialchars($result).".\n";
	 $nadaljuj = "ne";
}
*/
}




if($nadaljuj !== "ja") {
	$log .= "URL ni bil okrajšan. Glej napake zgoraj!";
} else {
$query = "INSERT INTO `".$tabela."` (`short`, `long`) VALUES ('".$safeshort."','".$safelong."');";
$result = mysqli_query($conn, $query);
// var_dump(mysqli_error($conn)); //debug


	//preveri uspeh
$query = "SELECT * FROM `".$tabela."` WHERE `short`='".$safeshort."';";
$result = mysqli_query($conn, $query);
if(mysqli_num_rows($result) == 0) {
	// var_dump(mysqli_error($conn)); //debug
	 $alert .= "<div class=alert>
  <span class=closebtn onclick=this.parentElement.style.display='none';>&times;</span> 
<b>Sistemska napaka!</b> Neznana napaka podatkovne baze.
</div><br>";
	 $log .= "Neznana napaka podatkovne baze. Glej sistemske dnevnike.\n";
} else {
	 $alert .= "<div class=alertok>
  <span class=closebtn onclick=this.parentElement.style.display='none';>&times;</span> 
<b>Uspešno!</b> Šortlink <b>".$domena."/".htmlspecialchars($_REQUEST['short'])."</b> je bil uspešno narejen!
</div><br>";
	 $log .= "Šortlink ".$domena."/".htmlspecialchars($_REQUEST['short'])." je bil uspešno narejen!\n";
	 
}

	
	
	}




} else {
	$log .= "Obrazec ni bil izpolnjen, zato samo prikazujem stran.\n";
}


$print .= "
<style>
.alert {
  opacity: 1;
  transition: opacity 0.6s; /* 600ms za izgine */
}
/* Škatla z obvestilom */
.alert {
  padding: 20px;
  background-color: #f44336; /* Rdeča */
  color: white;
  margin-bottom: 15px;
}

.alertok {
  padding: 20px;
  background-color: #43f436; /* Zelena */
  color: white;
  margin-bottom: 15px;
}

/* Gumb za zapreti */
.closebtn {
  margin-left: 15px;
  color: white;
  font-weight: bold;
  float: right;
  font-size: 22px;
  line-height: 20px;
  cursor: pointer;
  transition: 0.3s;
}

/* Ko je miška pod gumbom za zapreti */
.closebtn:hover {
  color: black;
}
</style>

<script>
// Dobi vse elemente z class=closebtn
var close = document.getElementsByClassName('closebtn');
var i;

// Pojdi čez vse gumbe za zapreti
for (i = 0; i < close.length; i++) {
  // Ko je gumb kliknjen
  close[i].onclick = function(){

    // Dobi starša od <span class=closebtn> (<div class=alert>)
    var div = this.parentElement;

    // Nastavi -prosojnost div-a na 0 (prozorna)
    div.style.opacity = 0;

    // Skrij div po 600ms (Ko izgine, izginotje je definirano tudi v CSS-ju)
    setTimeout(function(){ div.style.display = 'none'; }, 600);
  }
}
</script>

";
$print .= "
<title>ŠortLink Balkan</title>
<h1 align=center>ŠortLink Balkan</h1>
<h2 align=center>Ste kdaj hoteli narediti iz dolgega linka ŠortLink tako, da bi izgledal bolj balkansko?</h2>
<h2 align=center>Tudi če niste, je tukaj ŠortLink Balkan, edini Link Šortener, namenjen predvsem slovanskim narodom,saj za njegovo uporabo potrebujete črko Š!</h2>
<h3 align=center>Vsi Šortani linki se bodo začeli z š.ga, na primer š.ga/tekst. Najs ane?</h3>
<div align=center>
<form method=POST action=''>
	<input type=url name=long placeholder='Vpiši dolg URL ...' required=required align=center><br>
	".$domena."/<input type=text name=short placeholder='Vpiši krajšalnico ...' required=required align=center><br>
	<img id=captcha src=/securimage/securimage_show.php alt='Dostop samo ljudem. Prepiši znake iz slike, da potrdiš, da nisi program.' align=center /><br>
	<input type=text name=captcha_code size=10 maxlength=6 align=center/><br>
	<input type=submit name=submit value=Skrajšaj! align=center>
</form>
<br><small align=center>
ŠortLink Balkan za svoje delovanje potrebuje in uporablja sejne piškotke. Z uporabo storitve se strinajte z shranjevanjem piškotkov
v vaš brskalnik za največ 24 minut. Piškotek se uporablja samo za interni namen, torej za to, da izvemo katere črke si imel na preverjanju za ljudi (CAPTCHA)
in nikakor ne za namene vohunjenja (tracking cookies). Piškotki so vidni samo na domeni š.ga, torej samo našemu strežniku. To sporočilo smo vam po veljavnem EU
zakonu morali pokazati, ker sta Hrvaška in Slovenija v Evropski Uniji in morata zato upoštevati te glupe zakone.
</small>
</div>
";
$print .= "
<h4 align=center>Ker še nisem sprogramiral, ŠortLink Balkan še ne deluje. Ne uporabljaj ga, ker ne bo nič naredil.</h4>";




echo "<pre>" . $log . "</pre>"; // zakomentiraj to vrstico, da dnevnika ne boš prikazal, ali pa samo naredi HTML komentar, da lahko v sili še vedno pogledaš
echo $print;
echo $alert;
?>