Register a SA Forums Account here!
JOINING THE SA FORUMS WILL REMOVE THIS BIG AD, THE ANNOYING UNDERLINED ADS, AND STUPID INTERSTITIAL ADS!!!

You can: log in, read the tech support FAQ, or request your lost password. This dumb message (and those ads) will appear on every screen until you register! Get rid of this crap by registering your own SA Forums Account and joining roughly 150,000 Goons, for the one-time price of $9.95! We charge money because it costs us money per month for bills, and since we don't believe in showing ads to our users, we try to make the money back through forum registrations.
 
  • Post
  • Reply
KoRMaK
Jul 31, 2012



Back to a question I had to a little bit ago, how do I install rvm and gems so that ALL users or a subset of users use the same gemset? Is this a common pattern, where multiple users share gemsets or are you supposed to install it for each user?

Adbot
ADBOT LOVES YOU

Thalagyrt
Aug 10, 2006

KoRMaK posted:

Back to a question I had to a little bit ago, how do I install rvm and gems so that ALL users or a subset of users use the same gemset? Is this a common pattern, where multiple users share gemsets or are you supposed to install it for each user?

That'd require a lot of permission hackery. I've never seen a need to do that, though. What are you trying to accomplish?

KoRMaK
Jul 31, 2012



Thalagyrt posted:

That'd require a lot of permission hackery. I've never seen a need to do that, though. What are you trying to accomplish?
I'm probably doing it wrong that way then. I should probably just install it per user.

DONT THREAD ON ME
Oct 1, 2002

by Nyc_Tattoo
Floss Finder

KoRMaK posted:

Back to a question I had to a little bit ago, how do I install rvm and gems so that ALL users or a subset of users use the same gemset? Is this a common pattern, where multiple users share gemsets or are you supposed to install it for each user?

https://rvm.io/rvm/install

Search for 'multi-user'

Basically you install with sudo, create an rvm group, and then add users to the rvm group. I've never used it though.

KoRMaK
Jul 31, 2012



MALE SHOEGAZE posted:

https://rvm.io/rvm/install

Search for 'multi-user'

Basically you install with sudo, create an rvm group, and then add users to the rvm group. I've never used it though.
Yea I saw that, but it seems like not a good practice for some reason. I guess that my reason for feeling that way is that I don't see a reason to have more than 1 user be in charge of "rails" things.

necrotic
Aug 2, 2005
I owe my brother big time for this!

KoRMaK posted:

Yea I saw that, but it seems like not a good practice for some reason. I guess that my reason for feeling that way is that I don't see a reason to have more than 1 user be in charge of "rails" things.

You may be able to get that by making an rvm-ro group and giving it readonly access to the RVM install.

KoRMaK
Jul 31, 2012



I'm having a hard time with writing tests. I'm using rspec and capybara.

I have a remote script where the user clicks a link and it should download a file. I'm checking that the download directory changes the count of files in it. So I do

code:
expect{click_link "Download File"}.to change{ Dir.glob(File.join('/tmp/chromedownloads', "*.pdf")).length }.by(1)
The test finishes before the file downloads and says there is an error. How do I get it to wait.

OR

I can stash the count before I click the link, then compare it after to the current one. I'd really like to use the change command on the variable instead of should.

Thalagyrt
Aug 10, 2006

KoRMaK posted:

I'm having a hard time with writing tests. I'm using rspec and capybara.

I have a remote script where the user clicks a link and it should download a file. I'm checking that the download directory changes the count of files in it. So I do

code:
expect{click_link "Download File"}.to change{ Dir.glob(File.join('/tmp/chromedownloads', "*.pdf")).length }.by(1)
The test finishes before the file downloads and says there is an error. How do I get it to wait.

OR

I can stash the count before I click the link, then compare it after to the current one. I'd really like to use the change command on the variable instead of should.

I think you might want to rethink your test strategy. Why are you testing that the browser can download a file? That's not part of your application. Just make sure it's served up properly and call it done. Having a browser download a file and trying to make an assertion that the file's been downloaded is rather silly.

Edit: In the same vein, don't test ActiveRecord, don't test other external dependencies, but do test *your* code.

KoRMaK
Jul 31, 2012



Thalagyrt posted:

I think you might want to rethink your test strategy.
Yea, probably. The goal is to verify that we can verify that our app can send data to a third party, who turns it into a PDF, and then the user can download that PDF.

Thalagyrt posted:

Having a browser download a file and trying to make an assertion that the file's been downloaded is rather silly.
Why? I'm getting my mindset adjusted to testing, so I probably have a bunch of silly approaches that I need to get set straight on.


So my current problem is how do I verify that my communication to the third party goes well and that I get what I expect as a response?

I was writing these as feature tests, and it would *almost* work except that the DB cleaner and rspec is exiting before the response is finished.

kayakyakr
Feb 16, 2004

Kayak is true

KoRMaK posted:

Yea, probably. The goal is to verify that we can verify that our app can send data to a third party, who turns it into a PDF, and then the user can download that PDF.

Why? I'm getting my mindset adjusted to testing, so I probably have a bunch of silly approaches that I need to get set straight on.


So my current problem is how do I verify that my communication to the third party goes well and that I get what I expect as a response?

I was writing these as feature tests, and it would *almost* work except that the DB cleaner and rspec is exiting before the response is finished.

Technically the practice would probably be to mock the response from the 3rd party, then test the body of the response in your controller test to ensure that its payload is the file you expect.

You're not testing their interfaces, you're testing that you are responding to their interface correctly.

KoRMaK
Jul 31, 2012



The bummer about this is that it almost works. It's right there, I can see the file download in the selenium browser just before it closes. It was also the easiest approach and the least disruptive to the code. The other approaches will mean we have to restructure our code to be more testable, which will take more time. Structuring our code so that it is testable is definitely something I am working on, but for existing stuff I was hoping I could pop out a couple of feature tests quickly, so it's disappointing that I was able to get so close but not complete it.

Oh, and for reference, I got it working. Shortly after I posted that, I figured out how to get it to work by going with the second option and using page_execute to check if any ajax stuff was running, and if it was to wait.

This worked! But then I added another test that is very similar, and then the tests started taking turns failing. My current problem is that DB cleaner comes in too early and starts saying the test is over before it actually is.

KoRMaK fucked around with this message at 16:32 on Jun 26, 2015

Thalagyrt
Aug 10, 2006

KoRMaK posted:

Yea, probably. The goal is to verify that we can verify that our app can send data to a third party, who turns it into a PDF, and then the user can download that PDF.

Why? I'm getting my mindset adjusted to testing, so I probably have a bunch of silly approaches that I need to get set straight on.


So my current problem is how do I verify that my communication to the third party goes well and that I get what I expect as a response?

I was writing these as feature tests, and it would *almost* work except that the DB cleaner and rspec is exiting before the response is finished.

kayakyakr already covered it, but mock at any boundaries and test that your code responds to the boundaries properly. You don't need to test third party APIs. For the downloads, you don't need to test that the browser can download the file. If Chrome couldn't download a file, that's a bug in Chrome, not a bug in your code. Just use a controller test and assert that the right content type is set and other information relevant to the request. Beyond that, any browser will handle the download properly - so why waste time testing your browser?

KoRMaK
Jul 31, 2012



I guess if I had to defend it, it would be that we want to make sure that our users are getting what they expect, and that includes knowing if our third party vendors are hosed up.

Thalagyrt
Aug 10, 2006

KoRMaK posted:

I guess if I had to defend it, it would be that we want to make sure that our users are getting what they expect, and that includes knowing if our third party vendors are hosed up.

The majority of failures that'll arise when you're testing third parties will be random intermittent issues (throttling, network hiccups, maintenance, etc) and you're gonna end up pulling your hair out over random failures in your CI. Your tests should be deterministic. In order to have deterministic tests, you need to only test units under your control. That means mocking out *all* third party requests/responses. Work under the assumption that the third party will be working, and mock up specific failure scenarios so you know that you can gracefully handle third party APIs being down or otherwise erroring out.

DONT THREAD ON ME
Oct 1, 2002

by Nyc_Tattoo
Floss Finder
Testing is extremely difficult.


Also, I've been playing around in Crystal and it's wonderful.

Pardot
Jul 25, 2001




MALE SHOEGAZE posted:

Also, I've been playing around in Crystal and it's wonderful.

I never get excited about new tech, but for some reason this really has me. In all likelihood it will languish in obscurity, because that's the fate of most things, but I really hope not.

DONT THREAD ON ME
Oct 1, 2002

by Nyc_Tattoo
Floss Finder

Pardot posted:

I never get excited about new tech, but for some reason this really has me. In all likelihood it will languish in obscurity, because that's the fate of most things, but I really hope not.

I can see it catching on. The type inference seems really good so it basically just feels like you're writing ruby, except huge classes of errors are eliminated thanks to type checking.

In my opinion, crystal really addresses all of the worst things about Ruby. The lack of dynamism is addressed with macros, so you can still write powerful DSLs, but they're cleaner, more robust, and type safe.

Hughlander
May 11, 2005

KoRMaK posted:

I guess if I had to defend it, it would be that we want to make sure that our users are getting what they expect, and that includes knowing if our third party vendors are hosed up.

So what's actionable then?

You're about to commit code you just changed. Before you commit you run the test and it fails. What do you do before pushing? Do you push code that you know fails tests? Does your infrastructure ALLOW you to push code that fails tests? Replace commit with deploy. Will you deploy code that fails tests?

fantastic in plastic
Jun 15, 2007

The Socialist Workers Party's newspaper proved to be a tough sell to downtown businessmen.
Tangential to the testing conversation - is there a best practice for a situation like when your client has an API, you're building a new application that consumes that API, but the client's documentation is poo poo and the API often doesn't behave as specified?

It's not exactly the same case as we're discussing here, but a company I've worked with has tended to use tests touching the API to persuade intransigent clients that their API is, in fact, not behaving to specification. It tends to drive developers crazy because it can be hard to tell if the test is badly written or the API is wrong.

DONT THREAD ON ME
Oct 1, 2002

by Nyc_Tattoo
Floss Finder

Tao Jones posted:

Tangential to the testing conversation - is there a best practice for a situation like when your client has an API, you're building a new application that consumes that API, but the client's documentation is poo poo and the API often doesn't behave as specified?

It's not exactly the same case as we're discussing here, but a company I've worked with has tended to use tests touching the API to persuade intransigent clients that their API is, in fact, not behaving to specification. It tends to drive developers crazy because it can be hard to tell if the test is badly written or the API is wrong.

Testing foreign APIs is one of the hardest problems in computer science.

manero
Jan 30, 2006

Tao Jones posted:

Tangential to the testing conversation - is there a best practice for a situation like when your client has an API, you're building a new application that consumes that API, but the client's documentation is poo poo and the API often doesn't behave as specified?

It's not exactly the same case as we're discussing here, but a company I've worked with has tended to use tests touching the API to persuade intransigent clients that their API is, in fact, not behaving to specification. It tends to drive developers crazy because it can be hard to tell if the test is badly written or the API is wrong.

VCR will save your bacon here.

necrotic
Aug 2, 2005
I owe my brother big time for this!

KoRMaK posted:

I guess if I had to defend it, it would be that we want to make sure that our users are getting what they expect, and that includes knowing if our third party vendors are hosed up.

Use something like NewRelic to capture in-production issues (general response times, communication with 3rd-parties, etc..). As Thalagyrt said, testing 3rd parties in your actual tests is not good. You need your tests to be deterministic. For example, we had a test long ago that was checking some ranking algorithm that used rand in some scenarios. Instead of mocking the random number generator for deterministic results, the original spec tested for the value to be in a certain range (I think it was like 1%?), and it would randomly fail.

RobertKerans
Aug 25, 2006

There is a heppy lend
Fur, fur aw-a-a-ay.

manero posted:

VCR will save your bacon here.

I was just about to ask for advice on testing an API-dependent module, this looks awesome & exactly what I needed.

KoRMaK
Jul 31, 2012



Yea, vcr looks sweet.

Legacyspy
Oct 25, 2008
Hi, I don't consider myself to have knowledgeable coding practices. I have a question on model/view/controller.
The controller should not have significant code devoted to pulling data from the database and building hashes and lists out of it.
Stuff like that belongs in the model right? The controller should be small and just send stuff from the model to the view.

kayakyakr
Feb 16, 2004

Kayak is true

Legacyspy posted:

Hi, I don't consider myself to have knowledgeable coding practices. I have a question on model/view/controller.
The controller should not have significant code devoted to pulling data from the database and building hashes and lists out of it.
Stuff like that belongs in the model right? The controller should be small and just send stuff from the model to the view.

There are competing philosophies, in general, skinny controller is the more popular of the two.

I think the controller is in charge of translating what's coming in over the wire (queries) and knowing what the view needs to render a response. That often involves putting together a query and setting an instance variable for the view to render.

Take that for what you will.

Smol
Jun 1, 2011

Stat rosa pristina nomine, nomina nuda tenemus.
My 2c:

Models should dumb as gently caress. Don't make them "do" anything, just let them hold your data.

Controllers should only read the parameters, go get some stuff from database or whatever, return stuff to the browser. If it looks like you're doing more than that, do it in your service layer (which Rails unfortunately doesn't provide by default).

kayakyakr
Feb 16, 2004

Kayak is true

Smol posted:

My 2c:

Models should dumb as gently caress. Don't make them "do" anything, just let them hold your data.

Controllers should only read the parameters, go get some stuff from database or whatever, return stuff to the browser. If it looks like you're doing more than that, do it in your service layer (which Rails unfortunately doesn't provide by default).

There should be a few steps before switching to a service model:

Start doing the logic in the controller. A few heavy logic methods here and there are no big deal. If that gets too repetitive, switch to using concerns to keep it DRY. When you start to have too many concerns, then switch to a service model.

Chilled Milk
Jun 22, 2003

No one here is alone,
satellites in every home
Yeah it really depends on the details of what you're doing. If you're manipulating/translating a model's data, I'd much rather see that on the model itself rather the the controller.

But ideally yes you're introducing a new layer in between model and controller to house that logic, especially if it pertains to more than one model. If you're still getting a grasp on MVC that might be a bit too intense though.

Peristalsis
Apr 5, 2004
Move along.

The Milkman posted:

If you're still getting a grasp on MVC that might be a bit too intense though.

I think you've nailed it.


I've worked two jobs in a row using MVC architecture. The first one put all the logic in the controllers, and just used the model as a glorified wrapper for JDBC and SQL calls (this was with Java, Struts, and bunch of legacy Oracle PL/SQL code). My current job, using Ruby on Rails, uses controllers just to manage traffic, and puts all the business logic in the models. For what it's worth, the current, fat-model setup seems more intuitive and natural to me.

KoRMaK
Jul 31, 2012



I've gotten better at rspec/capybara/selenium

One tip I'd like to share that hung me up was that I was trying to see if something was on the page, so I was using has_selector? statements. Well it turns out that has_selector? WAITS to see if the element shows up and then throws a not found exception if it doesn't. Thats not what I wanted, I wanted to check if it's currently on the page and if it is or isn't do something. I wanted instant feedback, but instead it acts like an expect or should method. So I looked at the source for has_selector and it uses all() as it's base selector and then does some time waiting stuff. So then I looked at all, and verified that it returns immediately, which is what I wanted.

So if you are just checking if something is on the page, use all().

Chilled Milk
Jun 22, 2003

No one here is alone,
satellites in every home

Peristalsis posted:

I think you've nailed it.


I've worked two jobs in a row using MVC architecture. The first one put all the logic in the controllers, and just used the model as a glorified wrapper for JDBC and SQL calls (this was with Java, Struts, and bunch of legacy Oracle PL/SQL code). My current job, using Ruby on Rails, uses controllers just to manage traffic, and puts all the business logic in the models. For what it's worth, the current, fat-model setup seems more intuitive and natural to me.

Rails loves fat models, and for most of the projects you'd use Rails for that's fine. It's dependent on the scale you're working at. Testing that sort of stuff will be much easier if it's crammed into the model, than on the controller, so that's why I lean that way.

As long as you're 1) Keeping things readable 2) Keeping things granular 3) Keeping methods <5 lines and classes <100 you'll probably be fine.

Peristalsis
Apr 5, 2004
Move along.
Maybe this is more of an HTML question, but I thought I'd try this thread first, since the app is in Ruby on Rails.

I have a situation where our users basically want to be able to pass an arbitrary number of key-value pairs through a form post. That's fine, but I'm not sure what the best way do do that is, both in terms of the HTML widgets to use to accommodate the data entry, and how to pass the data through the post itself. I'm more interested in ease of implementation and readability than in being slick or efficient.

KoRMaK
Jul 31, 2012



Make their names "the_field[stuff_to_store][]" and it submits them as an array under params[:the_field][:stuff_to_store]

Peristalsis
Apr 5, 2004
Move along.

KoRMaK posted:

Make their names "the_field[stuff_to_store][]" and it submits them as an array under params[:the_field][:stuff_to_store]

Thanks. Any suggestions on how to handle the UI side of things?

Edit: Sorry if that's vague. I guess I'm asking if it's standard to use some sort of list widget and parse its contents by line, or to use some sort of expandable array of text boxes, or what.

KoRMaK
Jul 31, 2012



I would just add a button/link that hit some javascript which inserted more fields as needed.

Pollyanna
Mar 5, 2005

Milk's on them.


I came into my new job ready and eager to refactor everything in our Rails app, and within a month I had already ditched the idea and started playing with other languages and frameworks, exactly for those reasons regarding keeping everything granular and methods/classes small. All those guidelines are heavily violated. It's super daunting to have a massive codebase that is also not terrifically good. I actually kinda credit it with killing a lot of interest I had in Rails dev.

Now I'm doing my pet projects in Clojure and looking into big data and analytics topics. I feel like there's a better future there.

Less Fat Luke
May 23, 2003

Exciting Lemon
Don't worry, you can build a gigantic lovely codebase that becomes legacy in any language!

To be serious though Clojure is pretty cool; a lot of Ruby developers seem to gravitate towards it.

fantastic in plastic
Jun 15, 2007

The Socialist Workers Party's newspaper proved to be a tough sell to downtown businessmen.
If you plan your career well, you can be long gone before any of the lovely technical decisions and kludges you made to get version 1 working ever come back to bite you.

Adbot
ADBOT LOVES YOU

Smol
Jun 1, 2011

Stat rosa pristina nomine, nomina nuda tenemus.
Working with giant Rails codebases didn't make me gravitate towards clojure, but languages with highly expressive static type systems. Life is so much better now.

  • 1
  • 2
  • 3
  • 4
  • 5
  • Post
  • Reply