@@ -0,0 +1,135 @@ | |||
<?php | |||
namespace Controller; | |||
class Cart { | |||
private $basket; | |||
function __construct() { | |||
$f3 = \Base::instance(); | |||
$f3->route('POST /api/cart/add', '\Controller\Cart->add'); | |||
$f3->route('GET /api/cart/del', '\Controller\Cart->del'); | |||
$f3->route('GET /api/cart/more', '\Controller\Cart->more'); | |||
$f3->route('GET /api/cart/less', '\Controller\Cart->less'); | |||
$this->basket = new \Basket( 'cart' ); | |||
//$this->basket->drop(); | |||
} | |||
function index() { | |||
$f3 = \Base::instance(); | |||
$tmp = $this->basket->find(); | |||
$cart = []; | |||
foreach ($tmp as $i) { | |||
$cart[] = [ | |||
'name' => $i->get('name'), | |||
'price' => $i->get('price'), | |||
'amount' => $i->get('amount') | |||
]; | |||
} | |||
$cart_total = 0.0; | |||
foreach ($cart as $item) { | |||
$cart_total += $item['amount'] * $item['price']; | |||
} | |||
$f3->set('cart_meta',array_merge( | |||
$f3->get('cart_meta') ? : [], | |||
[ | |||
'cart_total' => $cart_total | |||
]) | |||
); | |||
$f3->set('cart', $cart); | |||
$this->sanitize_cart(); | |||
} | |||
function sanitize_cart() { | |||
$f3 = \Base::instance(); | |||
} | |||
function add() { | |||
$f3 = \Base::instance(); | |||
$caller = $f3->get('POST.caller'); | |||
$name = $f3->get('POST.name'); | |||
$price = $f3->get('POST.price'); | |||
$amount = $f3->get('POST.amount') ? : 1; | |||
$previously_in_cart = $this->basket->find('name',$name); | |||
if (count($previously_in_cart) > 0) { | |||
// item already in cart | |||
// add to counter | |||
$this->basket->load('name',$name); | |||
$this->basket->set('amount',$this->basket->get('amount') + $amount); | |||
$this->basket->save(); | |||
$this->basket->reset(); | |||
} else { | |||
$this->basket->set('name',$name); | |||
$this->basket->set('price',$price); | |||
$this->basket->set('amount',$amount); | |||
$this->basket->save(); | |||
$this->basket->reset(); | |||
}; | |||
//echo $caller; | |||
$f3->reroute($caller); | |||
} | |||
function del($name = false) { | |||
$f3 = \Base::instance(); | |||
$caller = $f3->get('GET.caller'); | |||
$name = $name ? : urldecode($f3->get('GET.name')); | |||
$this->basket->erase('name', $name); | |||
$f3->reroute($caller); | |||
} | |||
function more() { | |||
$f3 = \Base::instance(); | |||
$caller = $f3->get('GET.caller'); | |||
$this->change_quantity(1); | |||
$f3->reroute($caller); | |||
} | |||
function less() { | |||
$f3 = \Base::instance(); | |||
$caller = $f3->get('GET.caller'); | |||
$this->change_quantity(-1); | |||
$f3->reroute($caller); | |||
} | |||
function change_quantity($amount = 0) { | |||
$f3 = \Base::instance(); | |||
$caller = $f3->get('GET.caller'); | |||
$name = urldecode($f3->get('GET.name')); | |||
$this->basket->load('name', $name); | |||
$new_amount = $this->basket->get('amount') + $amount; | |||
if ($new_amount > 0) { | |||
$this->basket->set('amount',$this->basket->get('amount') + $amount); | |||
} else { | |||
$this->del($name); | |||
} | |||
$this->basket->save(); | |||
$this->basket->reset(); | |||
} | |||
function checkout() { | |||
$t = \Template::instance(); | |||
return $t->render('checkout.htm'); | |||
} | |||
} | |||
@@ -0,0 +1,269 @@ | |||
<?php | |||
namespace Controller; | |||
class Checkout { | |||
public $saksnummer; | |||
public $sak; | |||
public $DB = null; | |||
private $hydrated = false; | |||
function __construct($folder = null) { | |||
$f3 = \Base::instance(); | |||
$saksnummer = $f3->get('SESSION.saksnummer'); | |||
if ($saksnummer) { | |||
$this->saksnummer = $saksnummer; | |||
} else { | |||
$this->saksnummer = md5(sprintf("%s%f",$_SERVER['REMOTE_ADDR'],$_SERVER['REQUEST_TIME_FLOAT'])); | |||
$f3->set('SESSION.saksnummer', $this->saksnummer); | |||
} | |||
if (is_object($folder)) { | |||
$folder = $f3->get('POST.datapath'); | |||
} | |||
if (is_string($folder)) { | |||
$this->DB = new \DB\SQL(sprintf("sqlite:%sdatabase.sqlite",$folder)); | |||
} | |||
} | |||
function hydrate_framework_variables() { | |||
if($this->hydrated) { | |||
return false; | |||
} | |||
$f3 = \Base::instance(); | |||
$sak = new \DB\SQL\Mapper($this->DB,'saklist'); | |||
$a = new \DB\SQL\Mapper($this->DB,'addresses'); | |||
$contact = new \DB\SQL\Mapper($this->DB,'contacts'); | |||
$sak->load(['id=?', $this->saksnummer]); | |||
$f3->mset([ | |||
'full_cart' => $this->html_cart(), | |||
'contact' => $contact->load(['id=?',$sak->kContact]), | |||
'shipping' => $a->load(['id=?',$sak->kShipping]), | |||
'billing' => $sak->kBilling ? $a->load(['id=?',$sak->kBilling]) : $a | |||
]); | |||
$this->hydrated = true; | |||
} | |||
function overview() { | |||
$f3 = \Base::instance(); | |||
$tpl = \Template::instance(); | |||
$this->hydrate_framework_variables(); | |||
return $tpl->render('checkout_overview.htm',true); | |||
} | |||
function index() { | |||
$f3 = \Base::instance(); | |||
$sak = new \DB\SQL\Mapper($this->DB,'saklist'); | |||
if ($sak->load(['id=?',$this->saksnummer]) === false) { | |||
$sak->id = $this->saksnummer; | |||
$sak->save(); | |||
} | |||
if ($sak->kContact === null) { | |||
$f3->reroute('/checkout/contact'); | |||
} | |||
if ($sak->kShipping === null) { | |||
$f3->reroute('/checkout/shipping_address'); | |||
} | |||
return $this->overview(); | |||
} | |||
function save_address() { | |||
$f3 = \Base::instance(); | |||
$a = new \DB\SQL\Mapper($this->DB,'addresses'); | |||
$a->name = $f3->get('POST.name'); | |||
$a->address1 = $f3->get('POST.address1'); | |||
$a->address2 = $f3->get('POST.address2'); | |||
$a->zip = $f3->get('POST.zip'); | |||
$a->place = $f3->get('POST.town'); | |||
$a->country = $f3->get('POST.country'); | |||
$a->save(); | |||
return $a->id; | |||
} | |||
function save_contact() { | |||
$f3 = \Base::instance(); | |||
$a = new \DB\SQL\Mapper($this->DB,'contacts'); | |||
//$a->name = $f3->get('POST.name'); | |||
$a->email = $f3->get('POST.email'); | |||
$a->save(); | |||
return $a->id; | |||
} | |||
function place_order() { | |||
$info = new \DB\SQL\Mapper($this->DB,'info'); | |||
for ($i=0;$i<9999;$i++) { | |||
$candidate = strval(sprintf('%s%04d',date('Ymd'),$i)); | |||
if (!$info->load(['ordernumber=?',$candidate])) { | |||
$info->ordernumber = $candidate; | |||
$info->save(); | |||
break; | |||
} | |||
} | |||
return $info->id; | |||
} | |||
function email_to_merchant() { | |||
$f3 = \Base::instance(); | |||
$tpl = \Template::instance(); | |||
$c = $f3->get('checkout_data.emailconfig'); | |||
$subject = $f3->get('checkout_data.subject'); | |||
$smtp = new \SMTP( | |||
$c['host'], | |||
$c['port'], | |||
$c['scheme'], | |||
$c['user'], | |||
$c['pass'], | |||
); | |||
$headers = [ | |||
"MIME-Version"=>"1.0", | |||
"Content-type"=>"text/html", | |||
"From" => $c['from'] | |||
]; | |||
$smtp->set('To', $c['admin']); | |||
$smtp->set('Subject',$subject); | |||
foreach ($headers as $k=>$v) { | |||
$smtp->set($k,$v); | |||
} | |||
$f3->set('order_summary', $this->overview()); | |||
$f3->set('order_summary', $tpl->render('checkout_overview_kunde.htm',true)); | |||
$f3->set('UI', $f3->get('UI').";".$f3->get('form_path')); | |||
$email = $tpl->render($f3->get('checkout_data.template'),true); | |||
if ($smtp->send($email)) { | |||
return true; | |||
} else { | |||
return false; | |||
} | |||
} | |||
function email_to_client($recipient) { | |||
$f3 = \Base::instance(); | |||
$tpl = \Template::instance(); | |||
$c = $f3->get('checkout_data.emailconfig'); | |||
$subject = $f3->get('checkout_data.subject'); | |||
$smtp = new \SMTP( | |||
$c['host'], | |||
$c['port'], | |||
$c['scheme'], | |||
$c['user'], | |||
$c['pass'], | |||
); | |||
$headers = [ | |||
"MIME-Version"=>"1.0", | |||
"Content-type"=>"text/html", | |||
"From" => $c['from'] | |||
]; | |||
$smtp->set('To', $recipient); | |||
$smtp->set('Subject',$subject); | |||
foreach ($headers as $k=>$v) { | |||
$smtp->set($k,$v); | |||
} | |||
$f3->set('order_summary', $this->overview()); | |||
$f3->set('order_summary', $tpl->render('checkout_overview_kunde.htm',true)); | |||
$f3->set('UI', $f3->get('UI').";".$f3->get('form_path')); | |||
$email = $tpl->render($f3->get('checkout_data.template'), true); | |||
if ($smtp->send($email)) { | |||
return true; | |||
} else { | |||
return false; | |||
} | |||
} | |||
function buy() { | |||
$f3 = \Base::instance(); | |||
$sak = new \DB\SQL\Mapper($this->DB,'saklist'); | |||
$info = new \DB\SQL\Mapper($this->DB,'info'); | |||
$contact = new \DB\SQL\Mapper($this->DB,'contacts'); | |||
$sak->load(['id=?',$this->saksnummer]); | |||
$datapath = $f3->get('POST.datapath'); | |||
$sak->kInfo = $this->place_order(); | |||
$sak->status = 1; // 1 := ordernumber is generated | |||
$sak->save(); | |||
$info->load(['id=?',$sak->kInfo]); | |||
$contact->load(['id=?', $sak->kContact]); | |||
switch ($f3->get('POST.payment')) { | |||
case 'transfer': | |||
$email = new Email(); | |||
$email->load_form_config($f3->get('POST.xss-token')); | |||
//var_dump($f3->get('private')); | |||
if ($this->email_to_merchant() && | |||
$this->email_to_client($contact->email)) { | |||
$f3->set('SESSION',[]); | |||
$f3->reroute('/checkout/success'); | |||
} else { | |||
$f3->reroute('/checkout/failure'); | |||
} | |||
break; | |||
case 'paypal': | |||
break; | |||
} | |||
} | |||
function api(\Base $f3, $params) { | |||
$sak = new \DB\SQL\Mapper($this->DB,'saklist'); | |||
if ($sak->load(['id=?',$this->saksnummer]) !== false) { | |||
switch ($params['method']) { | |||
case "contact": | |||
$sak->kContact = $this->save_contact(); | |||
$sak->save(); | |||
$f3->reroute('/checkout'); | |||
break; | |||
case "shipping_address": | |||
$sak->kShipping = $this->save_address(); | |||
$sak->save(); | |||
$f3->reroute('/checkout'); | |||
break; | |||
case "billing_address": | |||
$sak->kBilling = $this->save_address(); | |||
$sak->save(); | |||
$f3->reroute('/checkout'); | |||
break; | |||
case "buy": | |||
$sak->status = $this->buy(); | |||
// $sak->save(); | |||
// $f3->reroute('/checkout/success'); | |||
default: | |||
break; | |||
} | |||
} | |||
} | |||
function html_cart() { | |||
$t = \Template::instance(); | |||
return $t->render("checkout.htm"); | |||
} | |||
} |
@@ -4,9 +4,9 @@ namespace Controller; | |||
class Email { | |||
var $c = []; | |||
var $data = []; | |||
var $path = ""; | |||
public $c = []; | |||
public $data = []; | |||
public $path = ""; | |||
function __construct() { | |||
@@ -21,6 +21,7 @@ class Email { | |||
if($formcall->load(['@token = ?', $token])) { | |||
$f3->config($formcall->form); | |||
$f3->set('form_path', $formcall->path); | |||
$this->path = $formcall->path; | |||
return true; | |||
} else { |
@@ -8,7 +8,8 @@ class CPublication extends ContentType { | |||
'TITLE' => 'title', | |||
'ARTIST' => 'artist', | |||
'DATE' => 'date', | |||
'IMAGE' => 'img' | |||
'IMAGE' => 'img', | |||
'CATALOGUE' => 'catalogue' | |||
); | |||
public $values; | |||
protected $layout; | |||
@@ -35,14 +36,19 @@ class CPublication extends ContentType { | |||
$img_html = sprintf('<img src="%s" alt="cover art" />', $img->get_src(1000)); | |||
return sprintf( | |||
"<div class=\"contentTypeElement publication\">" | |||
."<span class=\"catalogue\">%s</span>" | |||
."<a href=\"/%s\">" | |||
."%s" | |||
."<h2><a href=\"/%s\">%s</a><span class=\"artist\">%s</span>%s</h2>" | |||
."</div>", | |||
$img_html, | |||
$this->href, | |||
$v->title, | |||
$v->artist, | |||
$v->date ? '<span class="pubdate"> - '.$v->date.'</span>' : '' | |||
."<div class=\"info\">" | |||
."<h2>%s</h2><h3><span class=\"artist\">%s</span>%s</h3>" | |||
."</div></a></div>", | |||
$v->catalogue, | |||
$this->href, | |||
$img_html, | |||
$v->title, | |||
$v->artist, | |||
$v->date ? '<span class="pubdate"> - '.$v->date.'</span>' : '' , | |||
); | |||
} |
@@ -13,7 +13,7 @@ class FilesInFolders { | |||
private $EXT=array( | |||
'txt'=>array( 'txt', 'text', 'md' ), | |||
'pic'=>array( 'jpg', 'jpeg', 'png', 'svg' ), | |||
'tpl'=>array( 'html', 'htm', 'tpl' ), | |||
'tpl'=>array( 'html', 'htm' ), | |||
'audio'=>array('mp3','wav','ogg'), | |||
'csv'=>array( 'csv' ) | |||
); | |||
@@ -511,7 +511,7 @@ class FilesInFolders { | |||
} | |||
} | |||
} | |||
$f3->set('fields', | |||
array_merge( | |||
$fields, | |||
@@ -732,7 +732,46 @@ class FilesInFolders { | |||
//var_dump($new); | |||
} | |||
break; | |||
case 'buy': | |||
$new = ''; | |||
if(count($request)>=2) { | |||
$name=$request[1]; | |||
} else { | |||
$name ="item"; | |||
} | |||
if(count($request)>=3) { | |||
$price=$request[2]; | |||
} else { | |||
$price=1.0; | |||
} | |||
$fields = [ | |||
'caller' => $f3->get('page'), | |||
'name'=>$name, | |||
'price'=>$price, | |||
'amount'=>1 | |||
]; | |||
$hidden_inputs = []; | |||
foreach ($fields as $k=>$v) { | |||
$hidden_inputs[] = sprintf('<input type="hidden" name="%s" value="%s" />',$k,$v); | |||
} | |||
$new = sprintf('<form method="post" action="%s">%s<button action="submit" >BUY</button><span class="price"> %s</span></form>', | |||
'/api/cart/add', | |||
implode("\n",$hidden_inputs), | |||
$price ."€" | |||
); | |||
break; | |||
case 'checkout': | |||
$checkout = new \Controller\Checkout($this->folder); | |||
$new = $checkout->index(); | |||
break; | |||
case 'only_cart': | |||
$checkout = new \Controller\Checkout($this->folder); | |||
$new = $checkout->html_cart(); | |||
break; | |||
case 'image': | |||
$module = new CEimage($request, $body, $this->structs, $this->content); | |||
$new = $module->index(); |
@@ -0,0 +1,13 @@ | |||
<div class="cart"> | |||
<a href="/cart">cart</a> | |||
<repeat group="{{ @cart }}" key="{{ @key }}" value="{{ @value }}"> | |||
<li>{{ @value.amount }} x {{ @value.name }} à {{ @value.price }}</li> | |||
</repeat> | |||
<a href="/checkout">checkout</a> | |||
<script> | |||
</script> | |||
</div> |
@@ -0,0 +1,19 @@ | |||
<table> | |||
<repeat group="{{ @cart }}" key="{{ @key }}" value="{{ @v }}"> | |||
<tr> | |||
<check if="{{ isset(@page) }}"> | |||
<td><a href="/api/cart/less?name={{ urlencode(@v.name) }}&caller={{ @page}}">-</a> | |||
{{ @v.amount }} | |||
<a href="/api/cart/more?name={{ urlencode(@v.name) }}&caller={{ @page}}">+</a> | |||
</td> | |||
</check> | |||
<td> {{ @v.name }}</td> | |||
<td>{{ @v.price }} €</td> | |||
<td>{{ @v.amount * @v.price}} €</td> | |||
</tr> | |||
</repeat> | |||
<tr class="shipping"><td></td><td>shipping</td><td></td><td>{{ count(@cart) ? ( (@customVars.shipping_costs + (@cart.0.amount -1) * 10)): 0 }} €</td></tr> | |||
<tr class="summary"><td></td><td></td><td>total</td><td>{{ @cart_meta.cart_total + (count(@cart) ? ( (@customVars.shipping_costs + (@cart.0.amount -1) * 10)): 0) }} €</td></tr> | |||
</table> |
@@ -0,0 +1,37 @@ | |||
<table> | |||
<tr><th>contact</th></tr><tr><td>{{ @contact.email }}</td></tr> | |||
<tr><th><a href="/checkout/contact">change</a></th></tr> | |||
</table> | |||
<table> | |||
<tr><th>Shipping Address</th><th>Billing Address</th></tr> | |||
<tr> | |||
<td> | |||
{{ @shipping.name }}<br> | |||
{{ @shipping.address1}}<br> | |||
<check if="{{ @shipping.address2 }}"> | |||
{{ @shipping.address2}}<br> | |||
</check> | |||
{{ @shipping.zip}} {{ @shipping.place }}<br> | |||
{{ @shipping.country }}</td> | |||
<td> | |||
{{ @billing.name }}<br> | |||
{{ @billing.address1}}<br> | |||
<check if="{{ @billing.address2 }}"> | |||
{{ @billing.address2}}<br> | |||
</check> | |||
{{ @billing.zip}} {{ @billing.place }}<br> | |||
{{ @billing.country }}</td> | |||
</tr> | |||
<tr><th><a href="/checkout/shipping_address">change</a></th> | |||
<th><a href="/checkout/billing_address">change</a></th> | |||
</tr> | |||
</table> | |||
{{ @full_cart }} | |||
@@ -0,0 +1,33 @@ | |||
<table> | |||
<tr><th>contact</th></tr><tr><td>{{ @contact.email }}</td></tr> | |||
</table> | |||
<table> | |||
<tr><th>Shipping Address</th><th>Billing Address</th></tr> | |||
<tr> | |||
<td> | |||
{{ @shipping.name }}<br> | |||
{{ @shipping.address1}}<br> | |||
<check if="{{ @shipping.address2 }}"> | |||
{{ @shipping.address2}}<br> | |||
</check> | |||
{{ @shipping.zip}} {{ @shipping.place }}<br> | |||
{{ @shipping.country }}</td> | |||
<td> | |||
{{ @billing.name }}<br> | |||
{{ @billing.address1}}<br> | |||
<check if="{{ @billing.address2 }}"> | |||
{{ @billing.address2}}<br> | |||
</check> | |||
{{ @billing.zip}} {{ @billing.place }}<br> | |||
{{ @billing.country }}</td> | |||
</tr> | |||
</table> | |||
{{ @full_cart }} | |||
@@ -245,5 +245,8 @@ $f3->mset(array( | |||
debug("before run fatfree"); | |||
$bbb = new \Controller\Cart(); | |||
$bbb->index(); | |||
$f3->run(); | |||
echo \Template::instance()->render($f3->get('template')); |
@@ -1,5 +1,9 @@ | |||
[routes] | |||
GET /st = Controller\Checkout->index | |||
POST /api/checkout/@method = Controller\Checkout->api | |||
GET / = Controller\Page->home | |||
GET /home = Controller\Page->home | |||
GET /login = Controller\User->login | |||
@@ -9,3 +13,4 @@ GET /@level1/@level2 = Controller\Page->secondLevel | |||
GET /@level1/@level2/@level3 = Controller\Page->thirdLevel | |||
GET /@level1/@level2/@level3/@level4 = Controller\Page->fourthLevel | |||
POST /email = Controller\Email->send | |||