[addon webloader] Extras/webloader

2bfree
Člen | 248
+
0
-

uestla napsal(a):

Např. takhdlenc:

$css = new CssLoader();
if (Environment::isProduction()) {
	$css->filters[] = array($this, 'packCss');
}

ad komprimace výstupního HTML – použij např. helper TemplateHelpers::strip().

Asi jsem hloupý, ale v readme je:

<?php
protected function createComponentCss() {
    $css = new WebLoader\CssLoader;

    $css->sourcePath = WWW_DIR.DS."css";
    $css->tempPath = WWW_DIR.DS."webtemp";
    $css->tempUri = ((isset($_SERVER["HTTPS"]))&&($_SERVER["HTTPS"]!=""))? "https://".$_SERVER["SERVER_NAME"]."/webtemp" : "http://".$_SERVER["SERVER_NAME"]."/webtemp";
    $css->filters[] = function ($code) {
        return cssmin::minify($code, array("remove-last-semicolon"=>TRUE));
    };
    return $css;
}
?>

upravil jsem to na:

<?php
protected function createComponentCss() {
    $css = new WebLoader\CssLoader;

    $css->sourcePath = WWW_DIR.DS."css";
    $css->tempPath = WWW_DIR.DS."webtemp";
    $css->tempUri = ((isset($_SERVER["HTTPS"]))&&($_SERVER["HTTPS"]!=""))? "https://".$_SERVER["SERVER_NAME"]."/webtemp" : "http://".$_SERVER["SERVER_NAME"]."/webtemp";
    if(Nette\Environment::getName()=="production"){
        $css->filters[] = function ($code) {
            return cssmin::minify($code, array("remove-last-semicolon"=>TRUE));
        };
    }
    return $css;
}
?>

A na Development prostředí mám vygenerováno

<?php
<link rel="stylesheet" type="text/css" href="http://test.localhost/webtemp/cssloader-f6aef36945a5-screen.css?1290956224" />
?>

namísto očekávaného

<?php
<link rel="stylesheet" type="text/css" href="http://test.localhost/css/screen.css" />
?>

ad komprimace výstupního HTML mi vadí to, že tomu musím upravit generování šablon tak, že v @layout.phtml musím mít jenom

<?php
@{include content|strip}
?>

Tedy nemohu použít @layout.phtml pro layout jako takový

Honza Marek
Člen | 1664
+
0
-

Rozdíl je v obsahu toho vygenerovaného souboru.

2bfree
Člen | 248
+
0
-

Honza Marek napsal(a):

Rozdíl je v obsahu toho vygenerovaného souboru.

Proč se na Development prostředí generuje soubor namísto použití toho výchozího?

uestla
Backer | 799
+
0
-

Tak můžeš si buď stejně jako komprimaci nastavit public proměnnou Webloader::$joinFiles,

$css = new CssLoader();

if (Environment::isProduction()) {
	$css->joinFiles = FALSE;
}

nebo přímo v šabloně používat WebLoader jen při production módu…

{if Environment::isProduction()}
{widget css 'style.css'}
{else}
<link rel="stylesheet" type="text/css" href="{$basePath}/css/style.css">
{/if}

No a ten helper TemplateHelpers::strip() můžeš de facto použít i jako filtr…

// BasePresenter...
public function templatePrepareFilters($template)
{
	parent::templatePrepareFilters($template);
	$template->registerFilter('TemplateHelpers::strip');
}
2bfree
Člen | 248
+
0
-

Tak můžeš si buď stejně jako komprimaci nastavit public proměnnou Webloader::$joinFiles,

$css = new CssLoader();

if (Environment::isProduction()) {
	$css->joinFiles = FALSE;
}

nebo přímo v šabloně používat WebLoader jen při production módu…

{if Environment::isProduction()}
{widget css 'style.css'}
{else}
<link rel="stylesheet" type="text/css" href="{$basePath}/css/style.css">
{/if}

Tohle neřeší přesně to co jsem chtěl, ale děkuji za tip. Nakonec jsem to vyřešil následovně:

továrnička v presenteru:

<?php
protected function createComponentCss() {
    $css = new WebLoader\CssLoader;

    $css->sourcePath = WWW_DIR.DS."css";
    $css->sourceUri = ((isset($_SERVER["HTTPS"]))&&($_SERVER["HTTPS"]!=""))? "https://".$_SERVER["SERVER_NAME"]."/webtemp" : "http://".$_SERVER["SERVER_NAME"]."/css";
    $css->tempPath = WWW_DIR.DS."webtemp";
    $css->tempUri = ((isset($_SERVER["HTTPS"]))&&($_SERVER["HTTPS"]!=""))? "https://".$_SERVER["SERVER_NAME"]."/webtemp" : "http://".$_SERVER["SERVER_NAME"]."/webtemp";
    if(Nette\Environment::getName()=="production"){
        $css->filters[] = function ($code) {
            return cssmin::minify($code, array("remove-last-semicolon"=>TRUE));
        };
    } elseif(Nette\Environment::getName()=="development"){
        $css->joinFiles = FALSE;
    }
    return $css;
}
?>

Upravil jsem webloader tak, že jsem přidal proměnou sourceUri a upravil jsem metodu render() následovně:

<?php
public function render() {
    $hasArgs = func_num_args() > 0;

    if ($hasArgs) {
        $backup = $this->files;
        $this->clear();
        $this->addFiles(func_get_args());
    }

    // joined files
    if ($this->joinFiles) {
        $file = $this->generate($this->files);
        echo $this->getElement($this->tempUri . "/" . $file);
        // separated files
    } else {
        foreach ($this->files as $file) {
            if(\Nette\Environment::getName()=="development"){
                echo $this->getElement($this->sourceUri . "/" . \str_replace($this->sourcePath.DS,"",$file));
            } else {
                $file = $this->generate(array($file));
                echo $this->getElement($this->tempUri . "/" . $file);
            }
        }
    }
     if ($hasArgs) {
        $this->files = $backup;
    }
}
?>

výsledek je takový, že na produkčním prostředí se ty soubory všechny sloučí do jednoho a na vývojovém se použijí výchozí soubory ze sourcePath

No a ten helper TemplateHelpers::strip() můžeš de facto použít i jako filtr…

// BasePresenter...
public function templatePrepareFilters($template)
{
	parent::templatePrepareFilters($template);
	$template->registerFilter('TemplateHelpers::strip');
}

Díky, na tohle se podívám

Oggy
Člen | 306
+
0
-

znovu budu opakovat prosbu

ale používá někdo na cssloader less filtr? Aplikoval jsem ho podle návodu, ale nejede ..

<?php
 protected function createComponentCss() {
       $css = new CssLoader;
        ...
        $css->fileFilters[] = new LessFilter;
        ...
}
?>

děkuji za radu.

Honza Marek
Člen | 1664
+
0
-

defaultně webloader nemůže zohledňovat k cestě do vygenerovaného souboru jazyk, ale určitě by šla ta třída podědit, aby se to dělo.

ic
Člen | 430
+
0
-

Oggy napsal(a):

znovu budu opakovat prosbu

ale používá někdo na cssloader less filtr?

zkoušel jsem to, ale nic… taky na to nemůžu přijít

Jan Jakeš
Člen | 177
+
0
-

ic napsal(a):

Oggy napsal(a):

znovu budu opakovat prosbu

ale používá někdo na cssloader less filtr?

zkoušel jsem to, ale nic… taky na to nemůžu přijít

Pánové, zkoušeli jste zdrojovému CSS souboru změnit koncovku na .less? :)

Editoval Juan (25. 1. 2011 15:14)

ic
Člen | 430
+
0
-

to určitě zkusím

EDIT: @Juan Mě to funguje díky

Editoval ic (26. 1. 2011 11:52)

Felix
Nette Core | 1196
+
0
-

Funguje tu neco jako media? Potreboval bych u nejakych souboru nastavit print a u nekterych screen..

Honza Marek
Člen | 1664
+
0
-

Atribut media se dá nastavit, ale musíš potom mít dvě komponenty (printCss, screenCss).

Michalek
Člen | 211
+
0
-

Osobně to dělám takhle, jak píše Honza.

<?php
    protected function createComponentCss()
    {
        $css = new CssLoader;
        $css->media = 'screen, projection';
        // ... nastavení ...
        return $css;
    }

    protected function createComponentCssPrint()
    {
        $css = clone $this['css'];
        $css->media = 'print';
        return $css;
    }
?>

Editoval Michalek (30. 1. 2011 16:50)

whipster
Člen | 17
+
0
-

Prosím o radu, URL v CSS se mi absolutizuje špatně

viz http://localhost/Dispecinkpco/www%0Csssmoothnessimages/ui-bg_glass_75_e6e6e6_1x400.png

mělo by to být http://localhost/Dispecinkpco/www/css/smoothness/images/ui-bg_glass_75_e6e6e6_1x400.png

nemám žádní filtry , nejnovější verzi z GITHuB

používám nejnovější verzi Nette 2.0 Alpha 5.3 Nighty builds

Editoval whipster (13. 2. 2011 17:27)

Fergi
Člen | 14
+
0
-

whipster napsal(a):

Prosím o radu, URL v CSS se mi absolutizuje špatně......

Jsem na tom stejně… neví někdo kde by mohl být problém?

lupo112
Člen | 11
+
0
-

rata tento addon s moznou zmenou premennych? ako sa potom zachová?

lutor
Člen | 27
+
0
-

Zdravím, chtěl bych požádat o radu, jak doplnit regulár v CssUrlFilter.php ve funkci __invoke tak, aby nežral DataUri (např. v CSS mám url('data:image/png;base64,...), což filter vezme, a snaží se to zpracovat. Ve finále to dopadne tak, že soubor není zpracován a místo toho je vrácen null (bug?).

Konkrétně se jedná o regexp

$regexp = '~
		(?<![a-z])
			url\(                                     ## url(
				\s*                                   ##   optional whitespace
				([\'"])?                              ##   optional single/double quote
				(   (?: (?:\\\\.)+                    ##     escape sequences
					|   [^\'"\\\\,()\s]+              ##     safe characters
					|   (?(1)   (?!\1)[\'"\\\\,() \t] ##       allowed special characters
						|       ^                     ##       (none, if not quoted)
						)
					)*                                ##     (greedy match)
				)
				(?(1)\1)                              ##   optional single/double quote
				\s*                                   ##   optional whitespace
			\)                                        ## )
		~xs';
kravčo
Člen | 721
+
0
-

Upraviť by to šlo tak, že to odignoruje všetky URL začínajúce na data::

$regexp = '~
	(?<![a-z])
	url\(                                     ## url(
		\s*                                   ##   optional whitespace
		([\'"])?                              ##   optional single/double quote
		(	(?!data:)                         ##   ignore urls starting with `data:`
			(?:	(?:\\\\.)+                    ##     escape sequences
			|	[^\'"\\\\,()\s]+              ##     safe characters
			|	(?(1)	(?!\1)[\'"\\\\,() \t] ##       allowed special characters
				|       ^                     ##       (none, if not quoted)
				)
			)*                                ##     (greedy match)
		)
		(?(1)\1)                              ##   optional single/double quote
		\s*                                   ##   optional whitespace
	\)                                        ## )
~xs';

Ale treba povedať, že tento regulár by si zaslúžil zrefaktorovať, lebo efektivitou zrovna neoplýva :)

zarubik
Člen | 31
+
0
-

Prosím jak přidáváte další JS a CSS z dalších komponent?
Tak abych v layoutu mohl v <head> {control js} a {control css}.

V komponentě bych to chtěl mít v render(), tak abych mohl využívát i jiné rendry, než defaultní.

A pak se stává to, že komponenty, které se volají v <body> už se nepřidají javascripty a styly.
Funguje to pouze, když volání komponent dám až před </body>.

Zkoušel jsem obalit do bloku a includnout na začátku šabolny, ale pak se mi zobrazí 2× … kdyz definuju block pres „define“ tak se zase nacte az pri rendrovani v hlavicce :D

Snad jsem to napsal trosku srozumitelne. Diky za info, jak to pouzivate :)

Aurielle
Člen | 1281
+
0
-

Nedávej to do render ale nejlépe do metody attached(), nějak takto:

protected function attached($presenter)
{
	parent::attached($presenter);

	if($presenter instanceof Nette\Application\UI\Presenter) { // Komponenta může být připojena i k jiné komponentě, nejen k presenteru
		$presenter['css']->addFiles(array(...));
		$presenter['js']->addFiles(array(...));
	}
}
zarubik
Člen | 31
+
0
-

Super funguje :)
Jen se musí komponentat přidat přes addComponent a ne přes tovarnicku :)

Diky.

Kurtas
Člen | 109
+
0
-

Ahoj,
V poslední verzi (1.1) již neexistují tyto vlastnosti $cssLoader->sourceUri a $cssLoader->absolutizeUrls

Hlásí mi to vyjímku
Cannot write to an undeclared property WebLoader\CssLoader::$sourceUri

Nevím jestli by to vúbec pomohlo, ale špatně mi to upravuje cestu k obrázkům v css např

background: url('/ndibi/www/\css\../images/datagrid/icons/find.png') no-repeat right center;

Správně by mělo být

background: url('/ndibi/www/css/../images/datagrid/icons/find.png') no-repeat right center;

CssLoader mám nastaven takto:

$css = $header['css'];
$css->sourcePath = WWW_DIR . '/css';
$css->tempUri = $this->getHttpRequest()->url->baseUrl . 'temp';
$css->tempPath = WWW_DIR . '/temp';

Díky za pomoc

Jack06
Člen | 168
+
0
-

Vyřešili jste již někdo ten problém s url na obrázky? Díky

2bfree
Člen | 248
+
0
-

Stáhl jsem nejnovější Nette a pokusil se do něj implementovat webloader.

do config.neon jsem přidal následující

	services:
		robotLoader:
			option:
				directory: [%appDir%, %libsDir%]
			run: true

Do BasePresenter.php jsem dal následující

<?php
abstract class BasePresenter extends Nette\Application\UI\Presenter {
    protected function createComponentCss() {
        $css = new WebLoader\CssLoader;

        // cesta na disku ke zdroji
        $css->sourcePath = $this->getContext()->params['wwwDir'].DIRECTORY_SEPARATOR."css";

        // cesta na webu ke zdroji (kvůli absolutizaci cest v css souboru)
        //$css->sourceUri = $this->getHttpRequest()->url->baseUrl."css";

        // cesta na webu k cílovému adresáři
        $css->tempUri = $this->getHttpRequest()->url->baseUrl."webtemp";

        // cesta na disku k cílovému adresáři
        $css->tempPath = $this->getContext()->params['wwwDir'].DIRECTORY_SEPARATOR."css";

        // nastavení atributu media
        $css->media = 'screen, projection';

        return $css;
    }
}
?>

Narazil jsem na následující problémy:

  1. musel jsem zakomentovat nastavení atributů sourceUri jinak mám ten samý problém jako ostatní
  2. Vrací mi to chybu:

Use of undefined constant WWW_DIR – File: CssUrlsFilter.php Line: 28

Co se bodu 2 týče, vyřešeno nahrazením

<?php
$docroot = realpath(WWW_DIR);
?>

za

<?php
$docroot = realpath(Environment::getContext()->params['wwwDir']);
?>

Editoval 2bfree (9. 11. 2011 10:39)

h4kuna
Backer | 740
+
0
-

už jsem posílal pull ale nic :( případně zkus nějaký fork stáhnout

2bfree
Člen | 248
+
0
-

@kurtas @jack06: Co se absolutizace url v css týče, tak chyba je v souboru /libs/Extras/Webloader/filters/CssUrlsFilter.php kde na řádku 41 je zakomentován řádek, který je třeba odkomentovat

<?php
		$path = self::cannonicalizePath($path);
?>

Dále doporučuji zaměnit v tom samém souboru regulární výraz za ten, který píše @kravčo

Tomáš Votruba
Moderator | 1114
+
0
-

Mám takový problém, věřím, že je to nějaká prkotina.

  1. Plugin na slideshow + skript níže uvedený, které načítám přes <script src=... v pořádku fungují.
  2. {control js "jquery/jquery.bxSlider.min.js"} + skritp níže uvedený načítaný přes <script src=... také funguje
  3. {control js "jquery/jquery.bxSlider.min.js", "scripts.unlogged.js"}nefunguje

Kde by mohla být chybka?

<script>
$(document).ready(function() {

	var screenshow = $('#screenshow').bxSlider({
		mode: 'fade',
		auto: 'true',
		pause: 5000,
		controls: 'false',
		infiniteLoop: 'true',
		randomStart: 'true'
	});

	$('#go-prev').click(function(){
		screenshow.goToPreviousSlide();
		return false;
	});

	$('#go-next').click(function(){
		screenshow.goToNextSlide();
		return false;
	});

});
</script>

Díky.

2bfree
Člen | 248
+
0
-

Docela zajímavá technologie pro optimalizaci načítání javascriptu. Mohlo by stát za prozkoumání pro případné další využití.

http://www.andresvidal.com/jsl

Nox
Člen | 378
+
0
-

http://microjs.com/#… atd. … nevim jestli má někdo zkušenosti s více a může to porovnat

2bfree
Člen | 248
+
0
-

Probírám se teď optimalizací rychlosti načítání webu dle google page speed.
Uvažovali jste o tom, že by výstup JS componenty byl podle následujícího doporučení?
http://code.google.com/…ocs/rtt.html#…

22
Člen | 1478
+
0
-

mnozí z nás používají async loadery, např. head.js

2bfree
Člen | 248
+
0
-

Jinak mluvím o úpravě kódu v JavaScriptLoader.php

<?php
	/**
	 * Get script element
	 * @param string $source
	 * @return Html
	 */
	public function getElement($source) {
		//return Html::el("script")->type("text/javascript")->src($source);
		return Html::el("script")->type("text/javascript")->setText("
			var node = document.createElement('script');
			node.type = 'text/javascript';
			node.async = true;
			node.src = '$source';
			document.body.appendChild(node);
		");
	}
?>
mcmatak
Člen | 504
+
0
-

css a js obvykle zkládám z desítek souborů, obecné css pro flashes, obecné js pro notify, netteform, atd.

vzhledem k tomu, že filemtime a fileexist je dost drahá operace, nemáte někdo tip jak tomu ulehčit než aby to 30 s každým req. checkovalo filemtime?

alespon to zkrátit na 5 minutový úsek, ale nevím jak, jedine název souboru složený ze všech cest použitých souborů jeho md5 a uvnitř na prvním řádku poslední check, pokud nebude starší než 15min dejme tomu, tak nebudeme checkovat ostatní filemtime

má někdo lepší nápad? nebo způsob jak tohle provést?

Honza Marek
Člen | 1664
+
0
-

Začal jsem upravovat WebLoader tak, aby obstál v 21. století. K vidění je náhled na https://github.com/…e/webloader2. Je tam i readme, ze kterého se dá vykoukat nový způsob použití.

Co je nového:

  • unit testy
  • oku objektového programátora více lahodící kód
  • lepší rozšiřitelnost – jde snadněji vyměnit třeba pojmenování výsledného souboru
  • CSS urls filter je deprecated, protože s ním byly jen problémy (ale možná už nebudou, když jsou na něj napsané testy)
  • WebLoader je teoreticky schopný fungovat i bez Nette. Na Nette jsou závislé jen controly, co umí vypsat html tagy načítající kompilované soubory.
  • třídy Webloader\Compiler lze umístit do config.neon jako službu a následně je snadné např. generovat CSS v deploy scriptu ($container->cssLoader->generate())
  • časem bych se možná kouknul na možnosti nette rozšíření pro snadné nastavování css a js už v config.neon

Uvítám nějakou podnětnou odezvu (kromě stížností na nedodržení zpětné kompatibility ;) ). Nicméně není to zatím hotové. Funguje to, na co jsou testy.

Honza Marek
Člen | 1664
+
0
-

WebLoader 2.0 funkční.

Tomáš Votruba
Moderator | 1114
+
0
-

Skvělá práce, Honzo. Díky!

doplňcích to taky ještě updatneš?

E: Ještě mne napadlo, že by se v úvodním příspěvku hodil link na uvedení 2.0 – https://forum.nette.org/…as-webloader?p=7

Editoval Schmutzka (14. 2. 2012 16:09)

davidm
Člen | 81
+
0
-

Paráda!

Bylo by fajn přidat anotace k metodam createCssCompiler a createJsCompiler, aby fungovalo napovidani v netbeansech, jinak zatim vsechno funguje jak ma :)

davidm
Člen | 81
+
0
-

ještě k tomu url filtru, nešel by ten regulár nahradit timhle? btw určitě je škoda ho dávat deprecated, je to šikovná věc

https://github.com/…ssFilter.php#L49?

Honza Marek
Člen | 1664
+
0
-

Přímo s tím regulárem snad problémy nikdy nebyly, spíš se zbytkem filtru. Přijde ti ten z asseticu v něčem lepší?

Že je CssUrlsFilter teď deprecated znamená, že ho nepoužívám a není výchozí. Kdokoliv jinej klidně může. Mazat ho nebudu a když mi někdo potvrdí, že s nim nejsou problémy, tak klidně můžu to deprecated zase sundat.

Ivorius
Nette Blogger | 119
+
0
-

Jak mohu ten CssUrlsFilter použít? Koukal jsem do té třídy a __invoke($code, \WebLoader\Compiler $loader, $file = null). Co mám tedy předat v tom $code?

Zatím mám

$compiler = WebLoader\Compiler::createCssCompiler($files, WWW_DIR . '/webtemp');

$fil = new WebLoader\Filter\CssUrlsFilter(WWW_DIR, $this->template->basePath);
$compiler->addFilter($fil($code, $compiler));

Nebo případně máte jiný nápad, jak vyřešit cesty k background-url: když mám css v různých složkách?

Honza Marek
Člen | 1664
+
0
-

Předej jen $fil. Nebo můžeš psát ty CSS tak, že počítají s tím, že leží ve složce webtemp.

Ivorius
Nette Blogger | 119
+
0
-

Aha, díky. Hloupě jsem se nepodíval, že je na tom potom volána call_user_func

Platí ještě pořád pro přidání dalších css nebo js v komponentě návod, který uvedl gmvasek?

Honza Marek
Člen | 1664
+
0
-

To bude pořád fungovat. Ale nepovažuju to úplně za šťastný, protože se ti může generovat pro každou stránku jiný CSS, které se bude lišit několika řádkama CSS komponenty. Nebo dokonce jen pořadím CSS z komponent ve vygenerovaném CSS.

Ivorius
Nette Blogger | 119
+
0
-

Hm, to je pravda. V konečném důsledku asi nemá smysl pář řádků css řešit (nehledě na to, že po prvním načtení si to prohlížeč stejně drží v cache)

Ale co js knihovny? Takové jquery ui se už asi vyplatí načítat jen tam kde bude třeba ne? Nebo jak to řešíte?

Matúš Matula
Člen | 257
+
0
-

Ahoj,

nechces pridat gettery a settery do Webloaderu pre $compiler a $tempPath? Pouzivam Webloader na nacitavanie css a js napriec celou aplikaciou, kedy potrebujem menit fileCollection $compiler-u a vysledok ukladat do istej struktury, a teda menit aj $tempPath. Vyhol by som sa tak ‚zbytocnemu‘ instanciovaniu.

Honza Marek
Člen | 1664
+
0
-

ok, pošli pull

Honza Marek
Člen | 1664
+
0
-

WebLoader umí novej trik:

$files->addFiles(Finder::findFiles('*.css')->from(APP_DIR . '/templates'));
Tomáš Votruba
Moderator | 1114
+
0
-

Honza Marek napsal(a):

WebLoader umí novej trik:

$files->addFiles(Finder::findFiles('*.css')->from(APP_DIR . '/templates'));

Super, díky!

uestla
Backer | 799
+
0
-

S radostí se přidám k děkujícím a s velkým díky poděkuji za novou verzi ;-)

+ extra díky za vyřešení CSS URL filtru (jen jsem chvíli bádal než došlo na objevení addFileFilter()).

Honza Marek
Člen | 1664
+
0
-

Knihovnu WebLoader lze načítat přes package manager Composer – http://packagist.org/…ek/WebLoader