Deploying webapp on busy public server failing hard

classic Classic list List threaded Threaded
9 messages Options
Reply | Threaded
Open this post in threaded view
|

Deploying webapp on busy public server failing hard

Peter Hvass-3
Hello all,

The solution is kind of obvious here though I just wanted to feel around
for any alternatives.

I'm deploying a small web application to a Tomcat 8 server handled by
Amazon Web Service's Elastic Beanstalk service - load balancers etc. etc.

This is quite a busy site - so we'll typically see around 100 concurrent
users.

When I deploy a new version of the web app, the 'first load' is very heavy
- mostly due to LESS compilation (tapestry-webresources, wro4j). When 100
concurrent users hit for that 'first load' the server immediately falls
over in a 100% CPU death spiral.

My workaround thus far has been to deploy the new version to a secondary
server, access it for the first load myself and then throw it to the
hordes. This is annoying and time-consuming.

Ideally it would be great if LESS compilation could occur as part of
building the WAR file rather than live on the server. We never make changes
to files inside the WAR file directly. Has anyone been able to achieve this?

Kind regards,
Peter
Reply | Threaded
Open this post in threaded view
|

Re: Deploying webapp on busy public server failing hard

Cezary Biernacki
Hi Peter,
The simplest option is a create an empty page that just includes all
important CSS-es and JavaScripts and configure that page as a health check
URL in load balancer.

E.g.
Warmup.java:

@Import(stack = {"core"}, stylesheet = {"my.less"})
public class Warmup {
}

Warmup.tml

<html><head/><body/></html>


And /warmup defined in health-check. Because Amazon's load balancers first
need to hit health check URL at least a couple times before exposing an
instance, you can be sure that files are compiled/initialised before users
get access to your application. There are probably more clever ways to
solve your problem, but this one is quite easy.

Cezary




On Tue, Jul 5, 2016 at 3:07 PM, Peter Hvass <[hidden email]>
wrote:

> Hello all,
>
> The solution is kind of obvious here though I just wanted to feel around
> for any alternatives.
>
> I'm deploying a small web application to a Tomcat 8 server handled by
> Amazon Web Service's Elastic Beanstalk service - load balancers etc. etc.
>
> This is quite a busy site - so we'll typically see around 100 concurrent
> users.
>
> When I deploy a new version of the web app, the 'first load' is very heavy
> - mostly due to LESS compilation (tapestry-webresources, wro4j). When 100
> concurrent users hit for that 'first load' the server immediately falls
> over in a 100% CPU death spiral.
>
> My workaround thus far has been to deploy the new version to a secondary
> server, access it for the first load myself and then throw it to the
> hordes. This is annoying and time-consuming.
>
> Ideally it would be great if LESS compilation could occur as part of
> building the WAR file rather than live on the server. We never make changes
> to files inside the WAR file directly. Has anyone been able to achieve
> this?
>
> Kind regards,
> Peter
>
Reply | Threaded
Open this post in threaded view
|

Re: Deploying webapp on busy public server failing hard

Charlouze
In reply to this post by Peter Hvass-3
Hey,

I'm struggling with the same problem. I didn't took some time to address it
yet. I think that I've already sent an email on this mailing-list to ask
how could I compile less files at startup and not on demand but no one has
answered it.

I'd be glad to have a solution for that.

Cheers,
Charles Capon

Le mar. 5 juil. 2016 à 15:13, Peter Hvass <[hidden email]> a
écrit :

> Hello all,
>
> The solution is kind of obvious here though I just wanted to feel around
> for any alternatives.
>
> I'm deploying a small web application to a Tomcat 8 server handled by
> Amazon Web Service's Elastic Beanstalk service - load balancers etc. etc.
>
> This is quite a busy site - so we'll typically see around 100 concurrent
> users.
>
> When I deploy a new version of the web app, the 'first load' is very heavy
> - mostly due to LESS compilation (tapestry-webresources, wro4j). When 100
> concurrent users hit for that 'first load' the server immediately falls
> over in a 100% CPU death spiral.
>
> My workaround thus far has been to deploy the new version to a secondary
> server, access it for the first load myself and then throw it to the
> hordes. This is annoying and time-consuming.
>
> Ideally it would be great if LESS compilation could occur as part of
> building the WAR file rather than live on the server. We never make changes
> to files inside the WAR file directly. Has anyone been able to achieve
> this?
>
> Kind regards,
> Peter
>
Reply | Threaded
Open this post in threaded view
|

Re: Deploying webapp on busy public server failing hard

Dimitris Zenios
## Page Preloading

It is now possible to pre-load pages at system startup time by making
contributions
to the new PagePreloader service. Pages can be pre-loaded only in
development, only in production,
never, or always.


Quote from 5.4 release notes,Not sure if it will generate the js files at
the same time with pre loading.The other option is to do it the same way
tapestry core does it.i.e on development work with less files and on
production convert the less files to js before deployment (Through maven
plugin)

On Tue, Jul 5, 2016 at 5:47 PM, Charlouze <[hidden email]> wrote:

> Hey,
>
> I'm struggling with the same problem. I didn't took some time to address it
> yet. I think that I've already sent an email on this mailing-list to ask
> how could I compile less files at startup and not on demand but no one has
> answered it.
>
> I'd be glad to have a solution for that.
>
> Cheers,
> Charles Capon
>
> Le mar. 5 juil. 2016 à 15:13, Peter Hvass <[hidden email]> a
> écrit :
>
> > Hello all,
> >
> > The solution is kind of obvious here though I just wanted to feel around
> > for any alternatives.
> >
> > I'm deploying a small web application to a Tomcat 8 server handled by
> > Amazon Web Service's Elastic Beanstalk service - load balancers etc. etc.
> >
> > This is quite a busy site - so we'll typically see around 100 concurrent
> > users.
> >
> > When I deploy a new version of the web app, the 'first load' is very
> heavy
> > - mostly due to LESS compilation (tapestry-webresources, wro4j). When 100
> > concurrent users hit for that 'first load' the server immediately falls
> > over in a 100% CPU death spiral.
> >
> > My workaround thus far has been to deploy the new version to a secondary
> > server, access it for the first load myself and then throw it to the
> > hordes. This is annoying and time-consuming.
> >
> > Ideally it would be great if LESS compilation could occur as part of
> > building the WAR file rather than live on the server. We never make
> changes
> > to files inside the WAR file directly. Has anyone been able to achieve
> > this?
> >
> > Kind regards,
> > Peter
> >
>
Reply | Threaded
Open this post in threaded view
|

Re: Deploying webapp on busy public server failing hard

Ilya Obshadko
In reply to this post by Peter Hvass-3
My own solution was rotation of two DigitalOcean instances using floating
IP (you can do the same with AWS, Docker, etc.) whenever I do a deployment.
My project doesn't have heavy traffic (in that case, I'd consider some
LB-oriented solution, like HAProxy).

Everything, including startup and warm-up, can be easily automated using
deployment tools of your choice (for example, I'm using rake).

On Tue, Jul 5, 2016 at 4:07 PM, Peter Hvass <[hidden email]>
wrote:

> Hello all,
>
> The solution is kind of obvious here though I just wanted to feel around
> for any alternatives.
>
> I'm deploying a small web application to a Tomcat 8 server handled by
> Amazon Web Service's Elastic Beanstalk service - load balancers etc. etc.
>
> This is quite a busy site - so we'll typically see around 100 concurrent
> users.
>
> When I deploy a new version of the web app, the 'first load' is very heavy
> - mostly due to LESS compilation (tapestry-webresources, wro4j). When 100
> concurrent users hit for that 'first load' the server immediately falls
> over in a 100% CPU death spiral.
>
> My workaround thus far has been to deploy the new version to a secondary
> server, access it for the first load myself and then throw it to the
> hordes. This is annoying and time-consuming.
>
> Ideally it would be great if LESS compilation could occur as part of
> building the WAR file rather than live on the server. We never make changes
> to files inside the WAR file directly. Has anyone been able to achieve
> this?
>
> Kind regards,
> Peter
>



--
Ilya Obshadko
Reply | Threaded
Open this post in threaded view
|

Re: Deploying webapp on busy public server failing hard

Peter Hvass-3
In reply to this post by Peter Hvass-3
Hello all,

Sorry for the late response on this one!

About the warmup page - thanks! I am using this now - it bypasses the
issues I was facing with AWS ELB's health checks but still means a *very*
slow deployment time.

I had posted a similar issue from an old work address some time ago - look
for '5.4 LESS Coffee to CSS JS During Build Instead of First Access' on
this list. Howard replied saying this was outside Tapestry's scope and
suggested using WRO4J's maven plugin.

I'm aware that Tapestry used to include WRO4J as part of webresources but
then switched to less4j instead. I did some reading on the particular Maven
plugin for wro4j - it looks very fiddly indeed. Making sure it converts all
LESS files and dumps them right back where they were in the built war file
appears to be some kind of solution - I just haven't had the time (due to
work constraints) to investigate further yet. Has anyone else had any luck?

Regarding PageLoader - I tried this approach the other day - the sad thing
is ComponentSource.getPage (PageLoaderImpl uses this) did not seem to
trigger the compilation/minification etc. of assets (and so does not solve
our problem). To test this I supplied my warmup page which includes all of
the heavy LESS files in need of compilation.

Will do my best to investigate the wro4j maven plugin option - will report
back in case I figure something out - in the meantime if anyone else has
any other ideas or approaches I would be incredibly grateful!

Kindest regards,
Peter

On 5 July 2016 at 16:07, Peter Hvass <[hidden email]> wrote:

>
>> Hello all,
>>
>> The solution is kind of obvious here though I just wanted to feel around
>> for any alternatives.
>>
>> I'm deploying a small web application to a Tomcat 8 server handled by
>> Amazon Web Service's Elastic Beanstalk service - load balancers etc. etc.
>>
>> This is quite a busy site - so we'll typically see around 100 concurrent
>> users.
>>
>> When I deploy a new version of the web app, the 'first load' is very
>> heavy - mostly due to LESS compilation (tapestry-webresources, wro4j). When
>> 100 concurrent users hit for that 'first load' the server immediately falls
>> over in a 100% CPU death spiral.
>>
>> My workaround thus far has been to deploy the new version to a secondary
>> server, access it for the first load myself and then throw it to the
>> hordes. This is annoying and time-consuming.
>>
>> Ideally it would be great if LESS compilation could occur as part of
>> building the WAR file rather than live on the server. We never make changes
>> to files inside the WAR file directly. Has anyone been able to achieve this?
>>
>> Kind regards,
>> Peter
>>
>
>
Reply | Threaded
Open this post in threaded view
|

Re: Deploying webapp on busy public server failing hard

Dimitris Zenios
I thing your best solution is what you described.

Compile all less to css on building.

On Tue, Oct 25, 2016 at 4:36 PM, Peter Hvass <[hidden email]>
wrote:

> Hello all,
>
> Sorry for the late response on this one!
>
> About the warmup page - thanks! I am using this now - it bypasses the
> issues I was facing with AWS ELB's health checks but still means a *very*
> slow deployment time.
>
> I had posted a similar issue from an old work address some time ago - look
> for '5.4 LESS Coffee to CSS JS During Build Instead of First Access' on
> this list. Howard replied saying this was outside Tapestry's scope and
> suggested using WRO4J's maven plugin.
>
> I'm aware that Tapestry used to include WRO4J as part of webresources but
> then switched to less4j instead. I did some reading on the particular Maven
> plugin for wro4j - it looks very fiddly indeed. Making sure it converts all
> LESS files and dumps them right back where they were in the built war file
> appears to be some kind of solution - I just haven't had the time (due to
> work constraints) to investigate further yet. Has anyone else had any luck?
>
> Regarding PageLoader - I tried this approach the other day - the sad thing
> is ComponentSource.getPage (PageLoaderImpl uses this) did not seem to
> trigger the compilation/minification etc. of assets (and so does not solve
> our problem). To test this I supplied my warmup page which includes all of
> the heavy LESS files in need of compilation.
>
> Will do my best to investigate the wro4j maven plugin option - will report
> back in case I figure something out - in the meantime if anyone else has
> any other ideas or approaches I would be incredibly grateful!
>
> Kindest regards,
> Peter
>
> On 5 July 2016 at 16:07, Peter Hvass <[hidden email]> wrote:
> >
> >> Hello all,
> >>
> >> The solution is kind of obvious here though I just wanted to feel around
> >> for any alternatives.
> >>
> >> I'm deploying a small web application to a Tomcat 8 server handled by
> >> Amazon Web Service's Elastic Beanstalk service - load balancers etc.
> etc.
> >>
> >> This is quite a busy site - so we'll typically see around 100 concurrent
> >> users.
> >>
> >> When I deploy a new version of the web app, the 'first load' is very
> >> heavy - mostly due to LESS compilation (tapestry-webresources, wro4j).
> When
> >> 100 concurrent users hit for that 'first load' the server immediately
> falls
> >> over in a 100% CPU death spiral.
> >>
> >> My workaround thus far has been to deploy the new version to a secondary
> >> server, access it for the first load myself and then throw it to the
> >> hordes. This is annoying and time-consuming.
> >>
> >> Ideally it would be great if LESS compilation could occur as part of
> >> building the WAR file rather than live on the server. We never make
> changes
> >> to files inside the WAR file directly. Has anyone been able to achieve
> this?
> >>
> >> Kind regards,
> >> Peter
> >>
> >
> >
>
Reply | Threaded
Open this post in threaded view
|

Re: Deploying webapp on busy public server failing hard

Peter Hvass-3
Agreed Dimitris - upon build is indeed best!

There shouldn't be any inconsistencies provided I make sure both
tapestry-webresources and wro4j are using the same less4j version.

I imagine this will be a very standard pattern so I will aim to share the
working wro4j maven plugin configuration I end up with so others can use it
as an example.

Once again - if anyone has already got this working it would be amazing if
they could provide the rest with a shortcut by sharing their config!

Thanks,
Peter

On 26 October 2016 at 13:23, Dimitris Zenios <[hidden email]>
wrote:

> I thing your best solution is what you described.
>
> Compile all less to css on building.
>
> On Tue, Oct 25, 2016 at 4:36 PM, Peter Hvass <[hidden email]>
> wrote:
>
> > Hello all,
> >
> > Sorry for the late response on this one!
> >
> > About the warmup page - thanks! I am using this now - it bypasses the
> > issues I was facing with AWS ELB's health checks but still means a *very*
> > slow deployment time.
> >
> > I had posted a similar issue from an old work address some time ago -
> look
> > for '5.4 LESS Coffee to CSS JS During Build Instead of First Access' on
> > this list. Howard replied saying this was outside Tapestry's scope and
> > suggested using WRO4J's maven plugin.
> >
> > I'm aware that Tapestry used to include WRO4J as part of webresources but
> > then switched to less4j instead. I did some reading on the particular
> Maven
> > plugin for wro4j - it looks very fiddly indeed. Making sure it converts
> all
> > LESS files and dumps them right back where they were in the built war
> file
> > appears to be some kind of solution - I just haven't had the time (due to
> > work constraints) to investigate further yet. Has anyone else had any
> luck?
> >
> > Regarding PageLoader - I tried this approach the other day - the sad
> thing
> > is ComponentSource.getPage (PageLoaderImpl uses this) did not seem to
> > trigger the compilation/minification etc. of assets (and so does not
> solve
> > our problem). To test this I supplied my warmup page which includes all
> of
> > the heavy LESS files in need of compilation.
> >
> > Will do my best to investigate the wro4j maven plugin option - will
> report
> > back in case I figure something out - in the meantime if anyone else has
> > any other ideas or approaches I would be incredibly grateful!
> >
> > Kindest regards,
> > Peter
> >
> > On 5 July 2016 at 16:07, Peter Hvass <[hidden email]> wrote:
> > >
> > >> Hello all,
> > >>
> > >> The solution is kind of obvious here though I just wanted to feel
> around
> > >> for any alternatives.
> > >>
> > >> I'm deploying a small web application to a Tomcat 8 server handled by
> > >> Amazon Web Service's Elastic Beanstalk service - load balancers etc.
> > etc.
> > >>
> > >> This is quite a busy site - so we'll typically see around 100
> concurrent
> > >> users.
> > >>
> > >> When I deploy a new version of the web app, the 'first load' is very
> > >> heavy - mostly due to LESS compilation (tapestry-webresources, wro4j).
> > When
> > >> 100 concurrent users hit for that 'first load' the server immediately
> > falls
> > >> over in a 100% CPU death spiral.
> > >>
> > >> My workaround thus far has been to deploy the new version to a
> secondary
> > >> server, access it for the first load myself and then throw it to the
> > >> hordes. This is annoying and time-consuming.
> > >>
> > >> Ideally it would be great if LESS compilation could occur as part of
> > >> building the WAR file rather than live on the server. We never make
> > changes
> > >> to files inside the WAR file directly. Has anyone been able to achieve
> > this?
> > >>
> > >> Kind regards,
> > >> Peter
> > >>
> > >
> > >
> >
>
Reply | Threaded
Open this post in threaded view
|

Re: Deploying webapp on busy public server failing hard

Peter Hvass-3
An update on this - wro4j maven plugin is most certainly not the way to go
for any kind of a complex project.

It is highly restrictive when matching source files to be processed and
selecting destinations for the processed files.

You will only be happy with this solution if:

   - your stylesheet philosophy involves either;
   - having a monolithic single stylesheet
      - constantly maintaining your wro.xml to add new stylesheets as you go
   - and you're okay with the processed files being dumped into a single
   directory.
   - and you're also okay adding kludge to redirect all stylesheet import
   paths when in production mode toward this single directory.

I'm not happy with this as a solution - having looked into all the
available options I come back to thinking that Tapestry should either
support this or we need to add this functionality in ourselves as users.

That or wro4j needs some serious contributions - from what I understand the
reason destination folders are so restrictive is because wro4j's code for
wildcards in paths used for recursive file matching is deemed fragile.
There was an issue request to this effect and it was resolved by
side-stepping the problem and hard-coding rather than resolving it.

So my next step is likely to rewrite and/or override a portion of wro4j to
do this the way Tapestry does in development - just replacing all less
files with css at the same location.

Or writing my own plugin to achieve this;

   - traverse the directory structure
   - process all less files
   - store css files in their stead (i.e.: META-INF/assets/Some.less
   compiled to META-INF/assets/Some.less)

Thanks,
a very frustrated Peter

On 27 October 2016 at 11:12, Peter Hvass <[hidden email]> wrote:

> Agreed Dimitris - upon build is indeed best!
>
> There shouldn't be any inconsistencies provided I make sure both
> tapestry-webresources and wro4j are using the same less4j version.
>
> I imagine this will be a very standard pattern so I will aim to share the
> working wro4j maven plugin configuration I end up with so others can use it
> as an example.
>
> Once again - if anyone has already got this working it would be amazing if
> they could provide the rest with a shortcut by sharing their config!
>
> Thanks,
> Peter
>
> On 26 October 2016 at 13:23, Dimitris Zenios <[hidden email]>
> wrote:
>
>> I thing your best solution is what you described.
>>
>> Compile all less to css on building.
>>
>> On Tue, Oct 25, 2016 at 4:36 PM, Peter Hvass <[hidden email]>
>> wrote:
>>
>> > Hello all,
>> >
>> > Sorry for the late response on this one!
>> >
>> > About the warmup page - thanks! I am using this now - it bypasses the
>> > issues I was facing with AWS ELB's health checks but still means a
>> *very*
>> > slow deployment time.
>> >
>> > I had posted a similar issue from an old work address some time ago -
>> look
>> > for '5.4 LESS Coffee to CSS JS During Build Instead of First Access' on
>> > this list. Howard replied saying this was outside Tapestry's scope and
>> > suggested using WRO4J's maven plugin.
>> >
>> > I'm aware that Tapestry used to include WRO4J as part of webresources
>> but
>> > then switched to less4j instead. I did some reading on the particular
>> Maven
>> > plugin for wro4j - it looks very fiddly indeed. Making sure it converts
>> all
>> > LESS files and dumps them right back where they were in the built war
>> file
>> > appears to be some kind of solution - I just haven't had the time (due
>> to
>> > work constraints) to investigate further yet. Has anyone else had any
>> luck?
>> >
>> > Regarding PageLoader - I tried this approach the other day - the sad
>> thing
>> > is ComponentSource.getPage (PageLoaderImpl uses this) did not seem to
>> > trigger the compilation/minification etc. of assets (and so does not
>> solve
>> > our problem). To test this I supplied my warmup page which includes all
>> of
>> > the heavy LESS files in need of compilation.
>> >
>> > Will do my best to investigate the wro4j maven plugin option - will
>> report
>> > back in case I figure something out - in the meantime if anyone else has
>> > any other ideas or approaches I would be incredibly grateful!
>> >
>> > Kindest regards,
>> > Peter
>> >
>> > On 5 July 2016 at 16:07, Peter Hvass <[hidden email]>
>> wrote:
>> > >
>> > >> Hello all,
>> > >>
>> > >> The solution is kind of obvious here though I just wanted to feel
>> around
>> > >> for any alternatives.
>> > >>
>> > >> I'm deploying a small web application to a Tomcat 8 server handled by
>> > >> Amazon Web Service's Elastic Beanstalk service - load balancers etc.
>> > etc.
>> > >>
>> > >> This is quite a busy site - so we'll typically see around 100
>> concurrent
>> > >> users.
>> > >>
>> > >> When I deploy a new version of the web app, the 'first load' is very
>> > >> heavy - mostly due to LESS compilation (tapestry-webresources,
>> wro4j).
>> > When
>> > >> 100 concurrent users hit for that 'first load' the server immediately
>> > falls
>> > >> over in a 100% CPU death spiral.
>> > >>
>> > >> My workaround thus far has been to deploy the new version to a
>> secondary
>> > >> server, access it for the first load myself and then throw it to the
>> > >> hordes. This is annoying and time-consuming.
>> > >>
>> > >> Ideally it would be great if LESS compilation could occur as part of
>> > >> building the WAR file rather than live on the server. We never make
>> > changes
>> > >> to files inside the WAR file directly. Has anyone been able to
>> achieve
>> > this?
>> > >>
>> > >> Kind regards,
>> > >> Peter
>> > >>
>> > >
>> > >
>> >
>>
>
>