System.register(["@angular/core","@angular/material/core","@angular/cdk/coercion","@angular/common","rxjs","rxjs/operators","@angular/common/http","@angular/platform-browser"],(function(t){"use strict";var e,n,o,i,s,r,a,c,l,h,u,g,f,m,d,_,p,v,I,S,C,E,F,w,R;return{setters:[function(t){e=t.SecurityContext,n=t,t.Injectable,o=t.Optional,t.Inject,i=t.SkipSelf,s=t.ErrorHandler,r=t.InjectionToken,a=t.inject,t.Component,t.ViewEncapsulation,t.ChangeDetectionStrategy,t.Attribute,t.Input,t.NgModule},function(t){c=t.mixinColor,l=t.MatCommonModule},function(t){h=t.coerceBooleanProperty},function(t){u=t.DOCUMENT},function(t){g=t.of,f=t.throwError,m=t.forkJoin,d=t.Subscription},function(t){_=t.tap,p=t.map,v=t.catchError,I=t.finalize,S=t.share,C=t.take},function(t){E=t,F=t.HttpClient},function(t){w=t,R=t.DomSanitizer}],execute:function(){t({ICON_REGISTRY_PROVIDER_FACTORY:L,MAT_ICON_LOCATION_FACTORY:D,getMatIconFailedToSanitizeLiteralError:b,getMatIconFailedToSanitizeUrlError:x,getMatIconNameNotFoundError:y,getMatIconNoHttpProviderError:A});const N=["*"];function y(t){return Error(`Unable to find icon with the name "${t}"`)}function A(){return Error("Could not find HttpClient provider for use with Angular Material icons. Please include the HttpClientModule from @angular/common/http in your app imports.")}function x(t){return Error(`The URL provided to MatIconRegistry was not trusted as a resource URL via Angular's DomSanitizer. Attempted URL was "${t}".`)}function b(t){return Error(`The literal provided to MatIconRegistry was not trusted as safe HTML by Angular's DomSanitizer. Attempted literal was "${t}".`)}class T{constructor(t,e,n){this.url=t,this.svgText=e,this.options=n}}class M{constructor(t,e,n,o){this._httpClient=t,this._sanitizer=e,this._errorHandler=o,this._svgIconConfigs=new Map,this._iconSetConfigs=new Map,this._cachedIconsByUrl=new Map,this._inProgressUrlFetches=new Map,this._fontCssClassesByAlias=new Map,this._resolvers=[],this._defaultFontSetClass=["material-icons","mat-ligature-font"],this._document=n}addSvgIcon(t,e,n){return this.addSvgIconInNamespace("",t,e,n)}addSvgIconLiteral(t,e,n){return this.addSvgIconLiteralInNamespace("",t,e,n)}addSvgIconInNamespace(t,e,n,o){return this._addSvgIconConfig(t,e,new T(n,null,o))}addSvgIconResolver(t){return this._resolvers.push(t),this}addSvgIconLiteralInNamespace(t,n,o,i){const s=this._sanitizer.sanitize(e.HTML,o);if(!s)throw b(o);const r=s;return this._addSvgIconConfig(t,n,new T("",r,i))}addSvgIconSet(t,e){return this.addSvgIconSetInNamespace("",t,e)}addSvgIconSetLiteral(t,e){return this.addSvgIconSetLiteralInNamespace("",t,e)}addSvgIconSetInNamespace(t,e,n){return this._addSvgIconSetConfig(t,new T(e,null,n))}addSvgIconSetLiteralInNamespace(t,n,o){const i=this._sanitizer.sanitize(e.HTML,n);if(!i)throw b(n);const s=i;return this._addSvgIconSetConfig(t,new T("",s,o))}registerFontClassAlias(t,e=t){return this._fontCssClassesByAlias.set(t,e),this}classNameForFontAlias(t){return this._fontCssClassesByAlias.get(t)||t}setDefaultFontSetClass(...t){return this._defaultFontSetClass=t,this}getDefaultFontSetClass(){return this._defaultFontSetClass}getSvgIconFromUrl(t){const n=this._sanitizer.sanitize(e.RESOURCE_URL,t);if(!n)throw x(t);const o=this._cachedIconsByUrl.get(n);return o?g(O(o)):this._loadSvgIconFromConfig(new T(t,null)).pipe(_((t=>this._cachedIconsByUrl.set(n,t))),p((t=>O(t))))}getNamedSvgIcon(t,e=""){const n=U(e,t);let o=this._svgIconConfigs.get(n);if(o)return this._getSvgFromConfig(o);if(o=this._getIconConfigFromResolvers(e,t),o)return this._svgIconConfigs.set(n,o),this._getSvgFromConfig(o);const i=this._iconSetConfigs.get(e);return i?this._getSvgFromIconSetConfigs(t,i):f(y(n))}ngOnDestroy(){this._resolvers=[],this._svgIconConfigs.clear(),this._iconSetConfigs.clear(),this._cachedIconsByUrl.clear()}_getSvgFromConfig(t){return t.svgText?g(O(this._svgElementFromConfig(t))):this._loadSvgIconFromConfig(t).pipe(p((t=>O(t))))}_getSvgFromIconSetConfigs(t,n){const o=this._extractIconWithNameFromAnySet(t,n);if(o)return g(o);const i=n.filter((t=>!t.svgText)).map((t=>this._loadSvgIconSetFromConfig(t).pipe(v((n=>{const o=`Loading icon set URL: ${this._sanitizer.sanitize(e.RESOURCE_URL,t.url)} failed: ${n.message}`;return this._errorHandler.handleError(new Error(o)),g(null)})))));return m(i).pipe(p((()=>{const e=this._extractIconWithNameFromAnySet(t,n);if(!e)throw y(t);return e})))}_extractIconWithNameFromAnySet(t,e){for(let n=e.length-1;n>=0;n--){const o=e[n];if(o.svgText&&o.svgText.toString().indexOf(t)>-1){const e=this._svgElementFromConfig(o),n=this._extractSvgIconFromSet(e,t,o.options);if(n)return n}}return null}_loadSvgIconFromConfig(t){return this._fetchIcon(t).pipe(_((e=>t.svgText=e)),p((()=>this._svgElementFromConfig(t))))}_loadSvgIconSetFromConfig(t){return t.svgText?g(null):this._fetchIcon(t).pipe(_((e=>t.svgText=e)))}_extractSvgIconFromSet(t,e,n){const o=t.querySelector(`[id="${e}"]`);if(!o)return null;const i=o.cloneNode(!0);if(i.removeAttribute("id"),"svg"===i.nodeName.toLowerCase())return this._setSvgAttributes(i,n);if("symbol"===i.nodeName.toLowerCase())return this._setSvgAttributes(this._toSvgElement(i),n);const s=this._svgElementFromString("");return s.appendChild(i),this._setSvgAttributes(s,n)}_svgElementFromString(t){const e=this._document.createElement("DIV");e.innerHTML=t;const n=e.querySelector("svg");if(!n)throw Error(" tag not found");return n}_toSvgElement(t){const e=this._svgElementFromString(""),n=t.attributes;for(let t=0;tt)),I((()=>this._inProgressUrlFetches.delete(s))),S());return this._inProgressUrlFetches.set(s,a),a}_addSvgIconConfig(t,e,n){return this._svgIconConfigs.set(U(t,e),n),this}_addSvgIconSetConfig(t,e){const n=this._iconSetConfigs.get(t);return n?n.push(e):this._iconSetConfigs.set(t,[e]),this}_svgElementFromConfig(t){if(!t.svgElement){const e=this._svgElementFromString(t.svgText);this._setSvgAttributes(e,t.options),t.svgElement=e}return t.svgElement}_getIconConfigFromResolvers(t,e){for(let o=0;oe?e.pathname+e.search:""}}const k=["clip-path","color-profile","src","cursor","fill","filter","marker","marker-start","marker-mid","marker-end","mask","stroke"],H=k.map((t=>`[${t}]`)).join(", "),$=/^url\(['"]?#(.*?)['"]?\)$/;class W extends j{get inline(){return this._inline}set inline(t){this._inline=h(t)}get svgIcon(){return this._svgIcon}set svgIcon(t){t!==this._svgIcon&&(t?this._updateSvgIcon(t):this._svgIcon&&this._clearSvgElement(),this._svgIcon=t)}get fontSet(){return this._fontSet}set fontSet(t){const e=this._cleanupFontValue(t);e!==this._fontSet&&(this._fontSet=e,this._updateFontIconClasses())}get fontIcon(){return this._fontIcon}set fontIcon(t){const e=this._cleanupFontValue(t);e!==this._fontIcon&&(this._fontIcon=e,this._updateFontIconClasses())}constructor(t,e,n,o,i,s){super(t),this._iconRegistry=e,this._location=o,this._errorHandler=i,this._inline=!1,this._previousFontSetClass=[],this._currentIconFetch=d.EMPTY,s&&(s.color&&(this.color=this.defaultColor=s.color),s.fontSet&&(this.fontSet=s.fontSet)),n||t.nativeElement.setAttribute("aria-hidden","true")}_splitIconName(t){if(!t)return["",""];const e=t.split(":");switch(e.length){case 1:return["",e[0]];case 2:return e;default:throw Error(`Invalid icon name: "${t}"`)}}ngOnInit(){this._updateFontIconClasses()}ngAfterViewChecked(){const t=this._elementsWithExternalReferences;if(t&&t.size){const t=this._location.getPathname();t!==this._previousPath&&(this._previousPath=t,this._prependPathToReferences(t))}}ngOnDestroy(){this._currentIconFetch.unsubscribe(),this._elementsWithExternalReferences&&this._elementsWithExternalReferences.clear()}_usingFontIcon(){return!this.svgIcon}_setSvgElement(t){this._clearSvgElement();const e=this._location.getPathname();this._previousPath=e,this._cacheChildrenWithExternalReferences(t),this._prependPathToReferences(e),this._elementRef.nativeElement.appendChild(t)}_clearSvgElement(){const t=this._elementRef.nativeElement;let e=t.childNodes.length;for(this._elementsWithExternalReferences&&this._elementsWithExternalReferences.clear();e--;){const n=t.childNodes[e];1===n.nodeType&&"svg"!==n.nodeName.toLowerCase()||n.remove()}}_updateFontIconClasses(){if(!this._usingFontIcon())return;const t=this._elementRef.nativeElement,e=(this.fontSet?this._iconRegistry.classNameForFontAlias(this.fontSet).split(/ +/):this._iconRegistry.getDefaultFontSetClass()).filter((t=>t.length>0));this._previousFontSetClass.forEach((e=>t.classList.remove(e))),e.forEach((e=>t.classList.add(e))),this._previousFontSetClass=e,this.fontIcon===this._previousFontIconClass||e.includes("mat-ligature-font")||(this._previousFontIconClass&&t.classList.remove(this._previousFontIconClass),this.fontIcon&&t.classList.add(this.fontIcon),this._previousFontIconClass=this.fontIcon)}_cleanupFontValue(t){return"string"==typeof t?t.trim().split(" ")[0]:t}_prependPathToReferences(t){const e=this._elementsWithExternalReferences;e&&e.forEach(((e,n)=>{e.forEach((e=>{n.setAttribute(e.name,`url('${t}#${e.value}')`)}))}))}_cacheChildrenWithExternalReferences(t){const e=t.querySelectorAll(H),n=this._elementsWithExternalReferences=this._elementsWithExternalReferences||new Map;for(let t=0;t{const i=e[t],s=i.getAttribute(o),r=s?s.match($):null;if(r){let t=n.get(i);t||(t=[],n.set(i,t)),t.push({name:o,value:r[1]})}}))}_updateSvgIcon(t){if(this._svgNamespace=null,this._svgName=null,this._currentIconFetch.unsubscribe(),t){const[e,n]=this._splitIconName(t);e&&(this._svgNamespace=e),n&&(this._svgName=n),this._currentIconFetch=this._iconRegistry.getNamedSvgIcon(n,e).pipe(C(1)).subscribe((t=>this._setSvgElement(t)),(t=>{const o=`Error retrieving icon ${e}:${n}! ${t.message}`;this._errorHandler.handleError(new Error(o))}))}}static{this.\u0275fac=function(t){return new(t||W)(n.\u0275\u0275directiveInject(n.ElementRef),n.\u0275\u0275directiveInject(M),n.\u0275\u0275injectAttribute("aria-hidden"),n.\u0275\u0275directiveInject(z),n.\u0275\u0275directiveInject(n.ErrorHandler),n.\u0275\u0275directiveInject(P,8))}}static{this.\u0275cmp=n.\u0275\u0275defineComponent({type:W,selectors:[["mat-icon"]],hostAttrs:["role","img",1,"mat-icon","notranslate"],hostVars:8,hostBindings:function(t,e){2&t&&(n.\u0275\u0275attribute("data-mat-icon-type",e._usingFontIcon()?"font":"svg")("data-mat-icon-name",e._svgName||e.fontIcon)("data-mat-icon-namespace",e._svgNamespace||e.fontSet)("fontIcon",e._usingFontIcon()?e.fontIcon:null),n.\u0275\u0275classProp("mat-icon-inline",e.inline)("mat-icon-no-color","primary"!==e.color&&"accent"!==e.color&&"warn"!==e.color))},inputs:{color:"color",inline:"inline",svgIcon:"svgIcon",fontSet:"fontSet",fontIcon:"fontIcon"},exportAs:["matIcon"],features:[n.\u0275\u0275InheritDefinitionFeature],ngContentSelectors:N,decls:1,vars:0,template:function(t,e){1&t&&(n.\u0275\u0275projectionDef(),n.\u0275\u0275projection(0))},styles:["mat-icon,mat-icon.mat-primary,mat-icon.mat-accent,mat-icon.mat-warn{color:var(--mat-icon-color)}.mat-icon{-webkit-user-select:none;user-select:none;background-repeat:no-repeat;display:inline-block;fill:currentColor;height:24px;width:24px;overflow:hidden}.mat-icon.mat-icon-inline{font-size:inherit;height:inherit;line-height:inherit;width:inherit}.mat-icon.mat-ligature-font[fontIcon]::before{content:attr(fontIcon)}[dir=rtl] .mat-icon-rtl-mirror{transform:scale(-1, 1)}.mat-form-field:not(.mat-form-field-appearance-legacy) .mat-form-field-prefix .mat-icon,.mat-form-field:not(.mat-form-field-appearance-legacy) .mat-form-field-suffix .mat-icon{display:block}.mat-form-field:not(.mat-form-field-appearance-legacy) .mat-form-field-prefix .mat-icon-button .mat-icon,.mat-form-field:not(.mat-form-field-appearance-legacy) .mat-form-field-suffix .mat-icon-button .mat-icon{margin:auto}"],encapsulation:2,changeDetection:0})}}t("MatIcon",W);class B{static{this.\u0275fac=function(t){return new(t||B)}}static{this.\u0275mod=n.\u0275\u0275defineNgModule({type:B})}static{this.\u0275inj=n.\u0275\u0275defineInjector({imports:[l,l]})}}t("MatIconModule",B)}}})); Kasyno hazardowe Janusz jest w pelni spersonalizowane na polskich graczy, co dokladnie jest niewatpliwym plusem – Gavin Mostert Attorneys

Kasyno hazardowe Janusz jest w pelni spersonalizowane na polskich graczy, co dokladnie jest niewatpliwym plusem

Przedsiebiorstwa hazardowe pomaga ci tez powierzania wplat za pomoca popularnej na Polsce podejscia dla platnosci BLIK, co dokladnie jest wygodne i mozesz natychmiastowe. Dzieki temu sportowcy pochodza z dostep na licznych typow na najwyzszym poziomie gier, byc zwykle rozwijane i bedziesz uzupelniane w sprawie nowe marki.

Na stronie kasyno hazardowe obsluga vegas spins jest rowniez czesc FAQ ktorzy maja odpowiedziami na zwykle przesluchiwane pytania dotyczace profil, bonusow i mozesz uzywanie. Klaster jest korzystny i mozesz reaguje szybko, choc godziny dostepnosci czatu probuje ograniczone. W celu wygrana srodkow, obstawiajacy to zrobi miec poproszony w sprawie dostarczenie dokumentow potwierdzajacych tytul, wieki i bedziesz nazwa i adres. Minuty sa w tym samym czasie chronione pod wzgledem ze standardem PCI DSS.

Sportowcy w sprawie wysokich stawkach byli w stanie docenic system lojalnosciowy, i nowi zarejestrowani uzytkownicy z pewnoscia skorzystaja ktorzy maja jasnej sciezka weryfikacji i intuicyjnego interfejsu. Platforma podnosi sie masz staly i mozesz czysty wsparcie, dokladnie kto skutecznie pasuje rozlegla biblioteke gier ktorzy maja uczciwym podejsciem na bonusow i mozesz promocji. Produkty odpowiedzialnego hazardu, podobne limity depozytowe jesli samowykluczenie, sa dostepne w panelu gracza, dokladnie co swiadczy w sprawie dbalosci w sprawie bezpieczenstwo uzytkownikow. Obsluga klienta wykonuje sprawnie w godzinach z korzyscia, dostarczajac serwis przez kilka kanalow komunikacji, aczkolwiek czas do moze sie roznic w zaleznosci od wybranej podejscia dla zapytaj. Powtarzajace sie szkolenie z tych mechanizmow pozwala zachowac przepuscic w poprzek rozgrywka i mozesz zyski z niej satysfakcje indywidualnie jak wyniki.

Decyzja w sprawie grze z kasyno internetowe odzielnie okreslic, czy czy nie akceptujesz terror wynikajace ktorzy maja nie mam lokalnej licencji. W koncu niewystarczajace licencji Ministerstwa Finansow Polski to zrobi stymulowac watpliwosci, dziesiatki i tysiace polskich graczy posiadanie powodzeniem funkcji podobnych platform zamorski. Janusz przedsiebiorstwa hazardowe to solidna wyboru dla polskich graczy szukajacych kasyna online ktorzy maja hojnymi bonusami, szerokim uzywaniem gier oraz obsluga PLN. Janusz Casino autentyczne zdania pytajacego pojawia sie czesto wsrod polskich graczy, ktorzy chca ufac, jednego do ich fundusze jest stabilne, a gra wideo rozsadne. Wystarczajaco wejsc na januszcasino z powodu przegladarke mobilna (Safari, Chrome), a interfejs uzytkownika automatycznie dostosuje sie z rozmiaru ekranu.

Limity wyplat na Janusz Casino probuje zroznicowane w odniesieniu do statusu gracza oraz wybranej propozycje dla inwestowania. W Janusz Casino proces ten sa prosty, jednak wymaga wczesniejszej weryfikacji czlonkostwo – technologia informacyjna wazny jeden krok miec bezpieczny Wlasnych srodkow. Pomysl o jak mozesz, ze w przypadku, gdy ty potrzebujesz uwolnic dodatkowy bonus powitalny, powinienes zauwazyc odpowiednia dostarczam na zakladce bonusow przed dokonaniem wplaty.

Obstawiajacy otrzymuje zwykle niewielka kwote srodkow bonusowych lub po prostu po prostu program darmowych spinow, i to to zrobi wykorzystac na wybranych grach. Informacja mechanizmu produkty takich kodow pozwala mozna zapobiec awarie i mozesz realnie prognozowac wart otrzymanej zapewnia ci. Warte zachodu wszystko to samo wiedziec, ty na pewno posiadanie atrakcyjna nazwa kryja sie konkretne warunki obrotu, i dlatego nalezy zobaczyc tuz przed mozliwoscia wyplaty ewentualnych wygranych. Kody kuponow bez depozytu przyciagaja graczy pierwszy mozliwoscia przetestowania oferty bez potrzeby wplacania twoich srodkow.

Gry do Janusz przyjda czesto na forma demo (raczej niz logowania), jak i na prawdziwe pieniadze podazaniu dokonaniu wplaty. Od testowania system dysponowala wiecej 3000 tytulow jak renomowanych usluga oprogramowania. Janusz Casino nawet oferuje imponujaca biblioteke gier, ktora by rzeczywiscie zadowoli kazdego polskich graczy. Procedura odbierania bonusow w Janusz Casino jest wlasciwie prosty i latwy zajmuje doslownie par klikniec. Organizacja VIP znacznie zwieksza duch zespolowy gra i daje realny zyski z zwrotu na funkcji cashbacku oraz personalizowanych bonusow. W miare, duzy limit bonusu powitalnego (2500 zl) oraz reload bonusow (w 1000 zl) generuje, jednego do ktos wplacajace najbardziej stopien mogli polegac na znaczace naprzod konto.

W wlasciciela liczy sie przewidywalnosc srodki. Jedne gra online buduja cisnienie z powodu mnozniki, jakiekolwiek inne z powodu rundy bonusowe, symbole wild, funkcje scatter czy czy nie uklady free spins, a jeszcze dodatkowe opieraja atrakcja na prostocie i mozesz szybkim rozstrzygnieciu. Jakosc techniczna przeklada sie nie tylko na cialo, nawet tez do odczyt licznika parametrow gra, praca postaci bonusowych i mozesz cena ladowania sesji.

Nawigacja jest wlasciwie rownomiernie bulka ciasta � duzo bardzo wazne czesci ktore sa dostepne probuje teraz, raczej niz zbednego szukania

Wysypisko smieci odbywaja sie szybko z powodu popularne payment gateways, ze zredukowanym progiem piecdziesiat dolarow PLN dla bonusow. Warto nawet wiedziec, jednego fraza weryfikacji tozsamosci oraz realizacji transakcji mogli zmienic predkosc srodkow dostepu wygranych srodkow. Inicjowanie bonusow powitalnych i promocji stalych zobacz przejrzysta, choc profil musza dokladnie przejsc przez warunki istotne obrotu, aby uniknac nieporozumien z wyplata srodkow.

Z mojej stronie jest informacje dotyczace kasynach i mozesz grach, czesto do Polsce, jak i mozesz na calym swiecie

Tego typu styl utrzymuja semanticzna bliskosc terminow volatility i mozesz RTP w opisach, wzmacniajac topical authority. Ta inicjowanie buduje oddanie poprzez fair play i transparentnosc AML. Volatility gier slotowych pozwala strategiczne uzycie spinow, maksymalizujac RTP. Rollback wagering organizowany jest w srodku panelu uzytkownika, z opcja zapis poprawianie.

Wszystko jest intuicyjne i proste, tak nawet poczatkujacy sportowcy szybko odnajda sie na stronie. Charakterystyka swiadczone probuje naprawde i mozesz przejrzyscie, dobry zarobki realizowane jest terminowo za pomoca sprawdzonych sposoby wydatkow.

Mowa w sprawie roznych tysiacach tytulow, sa przyzwyczajeni do mam dolaczaja nowe. Oczywiscie, przedsiebiorstwa hazardowe oni ktore istnieja jest w trakcie jezyku polskim, od i mozesz mozesz ktorzy maja niego skorzystac na urzadzeniach mobilnych. Jest to mozliwe wlasciwie dostepnego wybor Graj ze Szwagrem, z powodu ktorej wchodzi sie na sesji ktorzy maja grami i mozesz zyskuje sie szanse na calkiem otwarte zyski. Srodki bonusowe oraz kwote wplaty nalezy zostac x25 do 30 dni, doskonaly zarobki ze spinow x35 do 3 dni. Przedsiewzieciem gracza jest wlasciwie kliknac na wybierz DEJ BONUSA, i dlatego robic depozytu do kwocie absolutne minimum piecdziesiat dolarow PLN. Free spiny posiadanie rejestracje ktore istnieja sa na grze Big Bass Vegas Double Pop muzyka Najwyzsza jakosc.

Janusz casino dodatkowy bonus bez depozytu pozwala graczom do rozpoczecie gra online zamiast wplacania jakichkolwiek srodkow do ranking. Jak, Janusz Casino jest w pelni ktore sa dostepne poprzez przegladarke na smartfonach i mozesz tabletach, dostarczajac responsywna i mozesz intuicyjna platforme mobilna. Dostepne jest ich wiele trzymac na ruletki, blackjacka, bakarata i pokera, ma tendencje do w roznych wariantach, co umozliwia pojednac rozgrywke z kilka wyboru i bedziesz budzetu. Organizacja natychmiast powiadamiaj w sprawie statusie transakcji, wlaczanie w pelna reke wzdluz procesem. Testujac proces Janusz casino wyplaty, zwrocilem szczegolna notatke na predkosci realizacji i ktore sa oferowane techniki dla. Najwiekszym zainteresowaniem ma Janusz casino lepiej deposit filip, aby rozpoczac gre bez koniecznosci wplaty srodkow.

Nizej niz bylo szczegolowy awaria kazdego etapu � od rejestracji przyjecia pierwsza produkuje. Sportowcy casino Janusz mogli skorzystac z cotygodniowego bonusu jedno C% od depozytu na wybrany tozsamosc, dostepnego do 4 razy do tygodniu. Na puli przyczyniaja sie granie z prawdziwych srodkow do wyznaczonych grach.

Message Us on WhatsApp