The supervisory authority Finansinspektionen, FI, has asked Klarna to explain what happened."
A future, fascinating post-mortem I hope!
The supervisory authority Finansinspektionen, FI, has asked Klarna to explain what happened."
A future, fascinating post-mortem I hope!
For me there are so many red flags with all these services, as they basically "steal" your credentials to log into your online banking. And while they claim that they only use the credentials to make transfers they could as well look at all my other account data. I really wonder how such a scheme can be legal and how banks can allow this, as they normally tell people to never give their credentials to anyone. The situation of course recently improved with the mandated 2FA for logins and transfers, but still there are so many attack vectors in this model that it boggles my mind how it can still exist.
But doing so has always been more confusing for me compared to “regular” payments with a credit card anywhere else, and has on overall been a negative experience for me.
I really don’t understand why anyone would prefer to use them at all.
What am I missing? Can anyone help me understand?
It says a lot about the security of their api and development culture that they are even struggling with something like this. This should be caught in the first architecture review session.
https://old.reddit.com/r/Steam/comments/3y7lxm/when_i_go_to_...
https://www.forbes.com/sites/insertcoin/2015/12/25/steam-is-...
0: https://github.blog/2021-03-18-how-we-found-and-fixed-a-rare...
With this, we know that Klarna's software quality is papier-mâché level. I am happy I refused to let Klarna have my account authorization.
We had built and authentication service that, among other things, was used by a SyncML service that was used back in the day of feature phones to syncs contacts etc. You can imagine that getting someone else's contacts on your phone isn't exactly ideal. This was how we came to know about the problem, from customers getting other customers data!
The error was caused by a CDN switch. Our instructions to the the CDN team responsible for the switch was "Make sure the CDN honors our cache headers, if our HTTP responses say something can be cached do so, if they say that the response should not be cached then don't". We were in at least three meetings where we repeated this mantra.
I believe that the CDN team thought that they had setup the CDN correctly but they had missed an edge case. The CDN was in fact setup to cache even uncacheable responses, and served those, _only_ when it could not reach our servers.
So if there was a traffic spike and the CDN determined that our authentication servers were unreachable it would fall back to serving data that should never have been cached in the first place! Happily returning tokens to random users that had authenticated just before the traffic spike...
Now I think they manage to track your devices so I only have to enter my postal code, and then I just click purchase, and it's all done.
They used to use really weird/dark patterns, to make you forget to pay and then pay huge fees to Klarna.
Nowadays as I've configured Klarna, it just subtracts the amount from my bank account, hassle free, and I don't have to do a bunch of reserach wether or not the website is credible.
Somewhat like Paypal, but smooother.
"Users of the payment service Klarna's app testify about disruptions on Thursday. Anyone who logs in with a bank ID has in many cases been able to see other people's information, including payments and invoices.
- It is very serious and violates privacy, says David Bjurhede, one of many who noticed the disturbances.
Many who have logged in with a bank ID on Klarna's app have on Thursday morning been able to get to someone else's account, users tell SVT Nyheter.
David Bjurhede is one of those who noticed that it was possible to see another person's information in the app, including what purchases had been made and parts of the account number. - It is very serious and violates privacy and risk of fraud if you can find out user information so easily, he says.
Another user says that he discovered the error at 11 o'clock and that it was possible to take part of other people's information for about 20 minutes. - It was possible to see almost everything, parts of the card details and exactly what they had bought and what their finances look like at Klarna. It's a little scary. I have not been through it before and I think it should not happen, he says."
The same can be applied to a credit card though so it's not a strong argument
Its the ID method I use for credits, pharmacies, health care, taxes, but was apparently not an ID so it's not id-hijacking.
Klarna has man in the middled my bank account before and performed a purchase and I've boycotting any company having them as the only payment option since.
OH, now I also remember Klarna adding credit in my name since they only needed my tax registered adress. I lived in a dorm so someone just used our public information to take out credits to order sneakers and could break into the crappy entry mailbox.
Sellers get paid immediately and they take care of making sure the customer pays.
Then again, PSD2 API roll-out has been very ???
(Not claiming it's a killer feature, but it's a feature.)
As to why it's popular with consumers looking at https://www.klarna.com/uk/smoooth/ , seems like they're offering months of interest free credit and also the implication is that using Klarna doesn't affect credit score.
It'd be interesting to know how their credit risk setup works.
I'm not sure what to think about this. My first thought is "Is this really legal?".
Before pushing to production please finish this code and choose the id you want to use:
"select * from users where id = ?"
> user_id
> profile_id
> user_profile_id
> profile_user_id
> id
> rand()
Once someone comes to their checkout they hide or at least make the direct payment options well hidden so that by default people buy by taking credit with them.
This credit often comes with shorter than industry standard payment terms so people end up missing payment and being handed over to their in-house collection agency that starts collecting overdue fees.
It's considered digitalized loansharking by many for a good reason.
Ironically it seems that for many smaller e-tailers using Klarna as the payment option seems to heighten the trust of customers so they're more likely to buy (my guess is that we've all been told or told people historically not to enter CC details on random sites and even with stuff like 3D-secure these days everyone is wary)
If someone should be aware of thread-local storage and its implication it ought to be them.
I agree in general that you need to enforce things at the storage layer.
They signed into users bank accounts, in other banks, to set up transfers (which also gives you all account statements).
The same NemID is also used to file your taxes, look at all your health info, get married, everything basically.
Credit card payments are much lower security level, and they're basically forcing sharing credentials amongst all the sites you pay on.
I talked to Klarna maybe 10 years ago. One of the things I wanted to know was how they dealt with abuse in Sweden, given you just need the social security number of a person and then you can do purchase as that person, and Swedish SSNs are not secret.
The friendly Klarna rep. had no idea what I meant, as you could only get stuff delivered to the address associated with the SSN. Based on how that would be abused in Denmark we suggested ordering a box of random sex toys to any random person in Sweden. The only answer I got was "Why would anyone do that?"
It took less than six month for Klarna to start asking us to block addresses, because they had no way to prevent abuse.
It's extremely useful for any ID verification, but Klarna asks you to verify your identity towards them but when you open the app they have instead sent a request to identify with your bank, using your credentials.
It was by choice. You weren't born with an account.
Not taking personal responsibility for the rise of the ubiquity of these terrible online services (WhatsApp users, I'm looking at you) is a huge part of the problem. Pretending that you didn't opt-in is a lie you've told yourself; you shouldn't propagate that lie to others in society.
Some banks used to require people to log into their banks to temporarily unlock their card for internet shopping, or, nowadays, one also needs to authenticate the purchase with the bank. That adds extra friction.
With Klarna one does not need to pay until 14 days after the goods are shipped. Credit cards are even better, but most people tend to just have a debit card. With Klarna they don't need to worry about spending too much money from the account and having some other payment bounce later on.
I personally stopped using them after I fell for one of their dark patterns and bought something on credit, which incurred an extra fee. Legally I was entitled to cancel the credit purchase, pay the full amount and avoid the fee; but I was still annoyed.
One e-shop I use regularly switched to Klarna and the whole checkout experience got much worse. Simple forms replaced by broken interactive ones, etc. It's still not better than the old UX, even after multiple iterations. I'm more reluctant to enter CC info than before, for what that's worth.
The situation in Europe is so bad that you are sometimes tricked into a prepaid order only to find out that the invoice comes from one of those.
The appropriate penalty is immediate cancellation and multiple GDPR requests.
Also, I figure they must be paying a lot of money to be the default payment provider on so many services.
For me, asking for my bank login details is...ridiculous - it'll be interesting to see if it is still following the same tactics in a few years.
I've never run a line of Dropbox code on any machine I own since that day. Even if you have no tests whatsoever on your app, you should have some basic smoke tests on your auth system.
https://www.theguardian.com/money/2018/nov/17/klarna-buy-now...
It's Payday Loans 2.0.
It's really disturbing to see Klarna as a payment option in many Dutch online shops. These always already have iDEAL (which the vast majority of customers use), a convenient way of doing an electronic bank transfer; and most shops support credit cards too.
We didn't need to scam anyone though, just have them verify that they were a Swedish resident (had a valid Swedish SSN and we're the ones ordering) :D
Would you have separate SQL credentials for each user, and configure SQL for each credential to have access to certain WHERE queries, or?
To simplify a use-case let's say I have "users" table and "tasks" table, where there's user_id in "tasks". Would I have separate sql credentials where they are configured in sql layer to have access to only rows where user_id corresponds to this certain credential? But even then how are credentials mapped to userId, as bug in application could easily cause retrieving false credentials?
Other way I can think of is to just have completely separate databases for each user, but let's in this case assume we must often do work with a mix of different users data.
Most banks have a paragraph in their contracts/ToS forbidding sharing the account with third parties, but they are rarely enforcing it. Still, they could close the account due to contract/ToS violation.
Is there more information on this? Are they doing the same thing Plaid does in the US? That is, literally asking for user credentials to internet banking instead of using the banks' proper APIs?
Further, they enable a "pay later by invoice" checkout flow, again by just knowing someone's SSN. Scammers use this to order items from web stores to automated pick-up lockers with someone's else's SSN for payment info. The victim usually only becomes aware about this activity when they start getting debt collection notices for unpaid invoices from multiple stores for thousands and thousands of euros. The debt collection process in Finland is famously unfair and harsh towards the supposed "debtor" (here: victim of fraud).
Unless the "debtor" (victim) actively opposes each and every individual collection, the cases will eventually end up in court with summary judgement. This will ruin the victim's credit rating, which has devastating results for just about all aspects of life. People are known to have collapsed under the burden of all this and ended up taking their own life.
Klarna's response to all this is that they want convenient checkout experience and some fraud is unavoidable. Although there are excellent technical means available to strongly identify users in Finland, they add a minor layer of inconvenience compared to just typing in your SSN. This is OK for Klarna since they give exactly zero fucks about security as long as they can make a little buck from it.
Major technical breakdown at Klarna when customers saw other people's data - The Swedish Financial Supervisory Authority (FI) has contacted the company
Payment giant Klarna, which has 87 million customers globally, is currently experiencing major technical problems. Users of the company's app saw other customers' payments and personal data, before it was shut down completely. The supervisory authority Finansinspektionen, FI, has asked Klarna to explain what happened.
In its app, Klarna has major technical problems. It means that users were logged into other customers' accounts and thereby see sensitive data such as their payment and purchase history and postal address. Users were also able to see part of the bank details linked to Klarna, but not the full account number.
One of Di's journalists accessed an account belonging to "Elisabeth". When the app was reloaded, another customer's login became visible.
When customers logged in with their own bank ID, they accessed other people's accounts. Each time they refreshed the page on the app, they brought up the details of a new, seemingly random user. It is unclear whether customers have been able to shop with other people's money.
Klarna had a total of 87 million consumers worldwide at the end of 2020, but it's unclear how many of those have an account on the company's app. The technical breakdown also extends beyond Sweden's borders, with outraged reactions pouring in on Twitter from Klarna users in various countries.
Klarna has now closed the app, citing a service outage. The company's press officer Niklas Gillström will return to Di after a while with a written comment.
"We are currently experiencing disruptions in our systems caused by technical problems. We are doing our utmost to restore the system and our services to full capacity and apologize for any inconvenience this may cause our customers. We have currently blocked all logins to the app until we are sure the problem has been fully resolved."
Di continues to seek the company for follow-up questions on whether the technical problems are due to an internal breakdown or external influence, how seriously the company views the sharing of personal data between users and whether customers may now have accidentally traded with other people's money. Klarna has asked for a response.
The Swedish Financial Supervisory Authority, FI, which among other things is the supervisory authority for banks, states that it has been informed of the situation.
"We have contacted Klarna and asked them for an explanation of what has happened," says Karin Lundberg, head of the business area Banking, to Di.
At the moment, FI has no further comments, she adds.
Di also seeks the Privacy Protection Authority, IMY, formerly known as the Data Inspectorate, for comment.
IMY has the right to fine companies up to 4 percent of their global annual turnover for serious violations. In addition, Klarna could face civil litigation, not least in the US where it has 15 million users.
(Translated with www.DeepL.com/Translator)
In OAuth2 David only ends up with some token showing Alice authorised David to use this service on her behalf. Bob can tell David and Alice apart, and choose to restrict what David can do appropriately.
If Bob is particularly tired of this nonsense, and his customers like Alice keep giving David their credentials and then are surprised that doing so means Bob can't tell Alice and David apart, WebAuthn reifies it so that most users in Alice's position can now see where the problem is. When David tells Alice he needs her Yubikey to access Bob's service, it should occur to Alice that giving the Yubikey to David isn't a good idea because then she won't have it any more. Good.
The session layer should confirm and only accept that the other SSL-endpoint is an authenticated app. The app should do this as well.
If a toggle box exists that can cause this, I'd wonder how much of else of the implementation is worth saving.
Mid process, they sent me some sort of timed bizarre IQ test that the recruiter claims EVERYONE who works there has to take.
That's when I knew that kind of working culture wasn't for me.
It may be different in different countries but the thing with the interest free credit is that once you don't pay on time it is converted into a revolving credit with high interest rate and something like a 60 months payment plan.
Klarna have also historically made up own names for fees to circumvent regulations for regulated fees. They were among the first to remove days of grace and among the first to use a fixed number of days from purchase to due date.
Compared to legacy finance, the exchanges are indeed bugfree. I would sooner trust Binance security team than people who think SMS is enough of a second factor. Never mind all the 'European unicorn' challenger 'banks'.
A merchant I shopped at, and paid in full by card, opened an account for me and shared line item details with Klarna, apparently because they are using them as their payments processor in addition to an installment payment option.
I noticed this when I later did in fact "open" an (or rather, claim an existing) account with them.
Very disturbing, and the bad aftertaste has never fully gone away.
With crypto, anything but perfect opsec on the entire stack through which your money travels means potentially losing all your money irreversibly. I’ll take “just use a database” thanks.
They provide "pay by bank account" (which involves the mentioned MITMing of users' online banking accounts, unless Klarna is integrated with your bank via OAuth/PSD2, which is still not ubiquitous), but also installment payments/factoring and others.
As far as I know most, if not all, of these scams have been perpetrated against the elderly. All operations (authentication, signing) can be initiated remotely with just a personal ID number, so the typical scam meant calling up someone and claiming that "an authentication must be performed", and simultanously initiating a bank login session. If you can keep the victim on the phone and using the BankID app when you tell them, you could basically login and empty their bank accounts. This has been largely fixed using QR codes to initiate login requests for major internet banks (which means you have to be in front of the same screen now) and other clever workarounds. But it has also always been a fact that there will be a description saying what you are signing, in the app, so being careful you could easily avoid being scammed.
I think its largely a great asset (BankID) but its never gonna be 100% tamper-proof without being seriously neutered.
[0] https://knowledge.fintecsystems.com/en/blog/the-history-of-o... , under "Legal Action by Giropay"
Its not like BitCoin and other Coins are free of scams/fraud because they are not regulated...
Most blockchains startups need to create problems which nobody has to sell it to people who don't know better...
Sounds like a poltergeist.
This meant that whenever two users signed in at the exact same time, there was a non-negligible chance that they swapped accounts during the flow.
It was actually not that easy to spot in the code. Sometimes what looks really, really stupid on the surface may in fact have a complicated and not-so-stupid explanation, often involving multiple developers and modernizing legacy code.
If it is a race condition, it can be incredibly hard to find during test.
Even if it is a stupid mistake, like e.g. not marking session cookies as secure and private, it does not mean that all of the rest of the code is bonkers.
https://en.wikipedia.org/wiki/Short_Payment_Descriptor
I don't see how credibility of website depends on what payment options they offer. That sounds like a separate issue.
Your marketing profile is tied in with their accounting system. The law requires them to store accounting data for at least 7 years, with no obligation to actually remove it once that time is up. Since the accounting laws supersede the GDPR: they can hoard data pretty effectively.
The Swedish 'Data Protection Authority' tried to launch (yet another) investigation for their shady practices, but Klarna strategically applied for bank status and now the reach and power of the data authority is cripplingly limited.
Unfortunately, they're huge, and I doubt the Swedish authorities will do more than give them a fine and a slap on the wrist.
It was discouraging.
Lesson 1: If someone want to sell you something and doesn't want make the bookkeeping itself, avoid them.
Lesson 2: In doubt? Cash only.
I just checked the chronology again: I performed the initial order months before opening the account, yet the line-level item details are there (and last time I checked, there was no way to delete these, for a payment years ago).
Oh, and I'm almost certain that somewhere within the fine print of paying at that store I consented to all of this, but this does not make it any less creepy from my point of view.
You mean through proof of stake instead? Yay, now all the people who wanted to avoid having a competent central bank in a free democracy control the money supply get to have the people with the most money control the supply instead.
Jesus fucking christ, you cryptocurrency lunatics have lost it.
For small businesses using a payment processor removes a massive barrier to market entry. Many small business hire real world external accountants to do their bookkeeping, so "avoiding actual work", would you avoid them as well? I do some work with the accounting & invoicing teams in our corporation and there is a LOT to take into account that would cripple a startup with only a handful of employees.
Bigger companies use services like Klarna not because they can't (often they have other payment methods as well and do their own bookkeeping), it's because customers like to use them and failing to use something like Klarna means their customers will shop elsewhere.
"developer gets a great idea - let's push an update to the API as a GET request so we can cache this on the CDN... forgetting that the JWT token is potentially returned in the call. Now, whoever makes the call first gets their JWT token stored for everyone else to load instead when the API call is made."
Ta-da, Klarna.
His assumption is surely, "Relax, what's going to happen, the cable won't break!".
I'm imagining it was a case of an SQL-based password check where "TRUE OR" got added to the WHERE clause, and the code takes the first result instead of expecting only 0 or 1 row.
Are there other easy ways to do this?
This points in the direction of this being a caching bug; you request your homepage, and get the homepage of whichever user was placed in the cache last.
Most of the time in these situations it's not an application-code issue (per-se), as much as a "shared global state" issue.
If you're assuming their user base is 50/50 male/female, which for many apps is not a valid assumption.
If I remember how to do math correctly, 50/50 gives 5 random users all being female ~4%. And 80/20 split is closer to 40%.
Here in Finland, It's not uncommon to have no debt apart from the mortage on one's home.
You can then accidentally click the wrong thing and buy without any further confirmation. At least in Sweden you can ask them to request digital ID confirmation for each buy.
With the current problem maybe I can buy using someone else's name...
Caching could be an issue, if they added a cache for a microservice call of /get/user?id=$USER and ignored the id parameter, /get/user?id=ipsin fetches data for the user ipsin, the system sees the next call /get/user?id=bellyfullofbac and thinks, "Wait, I have the results of /get/user in cache" and returns the data for ipsin again...
2) Mentioned elsewhere in this thread, a variable with global scope within an application server. This is very possible in node.js, which uses a long-running single thread - if you have a function like handleRequest(), you might inadvertently write to a global variable outside it, and that variable will persist across requests from different users. I've seen this exact bug in a PR - luckily we caught it before production, but if it had slipped through code review and integration tests and actually shipped, the result would have been exactly like the one in the tweet.
So what? It's 0% interest. It's incredibly helpful to have easy-access financing to split purchases across a few months.
>even simple things like buying a book through a web site requires declining several offers for paying with credit.
This sounds so specific it seems like you're taking a bad experience with one website and pretending all websites are like this. Most e-commerce sites I've used in the past year offer Klarna or some similar service and all of them have been implemented as just another option in a set of radio buttons.
Debit card payments are not debt - they're effectively the same as a direct transfer from the user's bank account.
I'm very conflicted about Klarna - on the one hand they do present an easy and (usually) safe way to handle transactions with small retailers to whom I don't necessarily want to share my payment details.
But on the other hand, they use a variety of dark patterns to try to get you to pay: 1. on credit 2. by signing-up for their credit-card
One unfortunate part of their earlier history, was that when you promised to pay with Klarna on a website, and was told you'd receive the invoice, there was a (perceived?) tendency for that invoice to never be sent due to an 'oversight'. When this happens in Sweden, the buyer gets a reminder a few days after the due-date, with a pretty large extra amount to pay.
There were quite a few stories about this in the press at various times [0], and I know quite a few people from Klarna and would tease them about it - which they always strenuously denied - but then it happened to me.
In any case, finding out how this happened is going to be interesting.
[0] in Swedish: https://www.svd.se/mangder-av-klagomal-mot-klarnas-fakturor
DeepL translation: "Lots of complaints against Klarna invoices. Klarna, the high-profile IT company, is being criticised by a host of customers. Many say they receive invoices with reminder fees and collection demands directly, without having been reached by an original invoice. The Swedish Consumer Agency is critical of Klarna's invoicing methods for several reasons and is currently investigating whether the company is behaving legally."
Translated with www.DeepL.com/Translator
Edit: typo
Debt is slavery and so on. Let's not get too hung up on the fact that I dislike it.
> Most e-commerce sites I've used in the past year offer Klarna or some similar service and all of them have been implemented as just another option in a set of radio buttons.
Radio buttons is fine. It's the defaults and "are you sure you don't want to pay with credit?" questions I'm bugged out about. I don't have an issue with them offering it as an option. I've seen it with multiple websites using Klarna for payment handling.
I thought that IQ test was screening test, pre-phone interview. But no, they had me redo it at the onsite interview too. The funny part was the onsite test had the exact same questions as pre-phone interview.
edit: typo
There are so many patterns(event driven, CQRS) in recent microservices architecture, which are gaining popularity and people have been using them without realizing the cons and the need for them.
I don't know, it seems like a failure at adulting to have to do that for small to medium sized purchases. If you need the feature, you probably should not have it available. Maybe this is my German attitude about money - basically, only take on debt for investments, a notable example being housing.
However, one common source for this kind of bugs is to ”cache any URL ending .pdf as a static file” and then you are in fact serving logged in PDFs like customer invoices that come with the session cookie.
I think CloudFlare used to come with a default rule to treat .pdf as a static content. The responses were cached when you hit their ”cache the good stuff” checkbox.
https://techcrunch.com/2015/01/29/itunes-connect-issue-loggi...
I remember doing it too. I was at work in a meeting and they have instructions saying something to the tune of finding a quiet place and all of that, but my thoughts were if they are serious about this, then solving these abstract problems is something I'll have to be able to do while under pressure or under the heat of conversation.
Long story short anyway, I'm not intelligent enough to work there I guess, so good thing they used that test to screen me out and make sure I knew. It does have a little bit of merit with the very quick no versus the long, drawn out no. I recently interviewed at a great company, 4 1-1 interviews, a presentation/demo I had to make to present to 7 other people, etc. and I think another interview after that and I'm just over it.
It had questions like "are you afraid of water", "have you showered in the last three weeks", "have you felt more aggressive lately"...
Any request for data or information regarding their architecture is rejected on the grounds of 'trade secrets'.
We immediately started getting reports of random products appearing in our customers' shopping carts, as people's sessions got merged with random strangers.
Singletons are easy to understand, as long as they contain of one simple class. But after a few iterations of development, they tend to "capture" a lot of dependencies, which practically become singletons too. A lot of mistakes happen. And most of the time, there was no good reason to create a singleton in the first place.
see also those posts: https://stackoverflow.com/a/138012/4249619 https://stackoverflow.com/a/142450/4249619
It's all about good engineering practice and architecture.
Some merchants sell via Klarna to private customers and via invoice or pre-payment to a proper bank account to business customers.
Private customers are second class. No business would deal with this nonsense.
Also by hipster, I mean that the banks don't have luxury to experiment with latest trends and the cool tools. They have to stick with the old proven methods.
Also, some customers do not have personnummer and find Klarna to be one of few payments methods that will reliably let them shop online.
I do know there are various legal requirements to retain certain data for some time (PSD2 for example must be stored for 13 months, I believe), but outside of that, it sounded to me like they tried very hard not to store anything for longer than necessary or without user consent.
I mean, doesn't mean its true, just the impression I got from the training.
That said, I'm also pro-nuclear.
A classic example: you need to get a user from a session, check against a database, and continue if they're signed in.
Then I add a simple if databaseUser.Username != form.Username and people will say "if that happens we've something worse wrong". Geez, something might be wrong and such double checking might provide to be useful.
On a smaller scale, bits flip due to cosmic rays and so on. Of course, there must be a limit where we stop, but people are used to actively avoid doing such "silly assertions" even for important steps.
¯\_(ツ)_/¯
create a social media site - allow postings, conversations, threads, etc.
Every quarter (or some other period), there is "reconning". You are placed into a complete stranger's account, and now you have to continue it for a week (or some other short period).
Whoever can maintain the quality of the account, in the direction as the original owner, wins a banana (or kumquat, something good but not expensive for anyone).
After reconning period, owner returns and judges. None-participation is default no-win.
https://www.klarna.com/uk/blog/written-statement-on-app-bug/
Although I dunno about "According to GDPR standards, only non-sensitive data was exposed." since in the twitter thread someone said:
This is definitely not a test environment. I was called by someone who was logged in to my account and saw all my personal data including bank details, Klarna card etc.
And while I'm told the bank details are obfuscated (I don't use Klarna, I dunno), I would consider the phone number to be a clear breach of my privacy under GDPR.
Although, the twitter account that said that has 0 followers, so maybe its not true. I dunno. I know someone who works for Klarna and he told me: "Full investigation will take time. There's a LOT of engineers working on this. Only confirmation I have currently is that the firstname was visible."
Going by the screenshots, first name and account balance. Doesn't seem that bad from a GDPR point of view. Still bad, of course, but not suuuper sensitive.
EDIT: Nevermind: https://twitter.com/esraefe/status/1397843949985931265
1. They MUST NOT allow more than one instance. "I don't think anyone will ever need more than one" isn't enough. Just create only one instance then. Only enforce single instance if there is a requirement for it. For example, a logger is a bad singleton because you could conceivably want more than one instance. Something that requires exclusive access to some hardware may be a good candidate though.
2. The instance must be globally accessible. Many things don't need to be globally accessible though.
So unless you need a global enforced-single-instance of something, which in my ~20 years of programming is rarely needed, a singleton is a bad choice. In my experience, many times someone wanted only one instance, some time later it turns out that actually multiple instances would be useful after all (separate loggers for separate types of logs for example).
In most cases where singletons are used, a simple global would have sufficed. If you only want one instance, then create only one instance. If you need lifecycle management, then do something for that.
Those SO posts cover it nicely.
Lessons learned the hard way ;)
But... API's really shouldn't be cached? At least not at the CDN level. The risk of serving up stale dashboard data alone makes users go ????... and we definitely don't want - not even mentioning the problem here, that's crazy.
Quickly why they don't work:
You create a huge chain correlational assumptions. First that visual-spatial tasks of this kind predict performance on visual tasks. 2. That performance on visual tasks predict general intelligence (whatever that is). 3. That this notion of general intelligence (which is usually and arbitrarily defined not to include social skills) actually correlates with the tasks that you think the person will be performing, and finally that your idea of what the role has an impact on the company. Of course it is completely absurd, what they are selling is snake oil, plain and simple.
The remedy I recommend is simple, talk to the person - do it and you will be able to tell within 5 minutes.
If you have other information about other reasons they might have become a bank, I would be genuinely interested in hearing them.
https://www.atlassian.com/incident-management/postmortem/bla...
Or perhaps not
https://techbeacon.com/app-dev-testing/blameless-postmortems...
> The bug led to random user data being exposed to the wrong user when accessing our user interfaces. It is important to note that the access to data has been entirely random and not showing any data containing card or bank details (obfuscated data was visible). This means that it has been impossible to access a specific user’s data.
This is not the experience of the user in the OP: https://twitter.com/esraefe/status/1397843949985931265
EDIT: that's how firesheep (https://en.wikipedia.org/wiki/Firesheep) hijacked sessions for e.g.
https://biology.stackexchange.com/questions/16749/why-does-r...
Specifically, if you have data that is loaded from some other source, your extra safety check might be checking data that's loaded from the same source, in a way where if something did go wrong, it went wrong in both places you're checking.
In this case, it seems pretty unlikely that Klarna's bug was that they ran "SELECT * FROM users WHERE Username = 'joeuser'" and they got back a row where Username != 'joeuser'. I don't think there's a recorded case of that ever happening with databases.
However, it seems much more likely that Klarna's bug was in HTTP caching or something, that results were returned for the wrong user. Then there's no opportunity to see databaseUser.Username != form.Username: that check would have indicated that things are correct, but the username being passed into this code was wrong in the first place. That sort of problem definitely happens in the wild - see the "Kenneth" story elsewhere in these comments, or off the top of my head https://blog.zulip.com/2021/03/20/zulip-cloud-security-incid... from two months ago.
And if it is, somehow, a database bug, why do you trust the database at that point? What if the database returns part of one row and part of another? What if it returns the username you sent in because of some optimization to avoid copying data, but thanks to a bug (or a cosmic ray) it reads in the rest of the data from an unrelated row? In the unlikely but not totally impossible case that you need to protect yourself against this, validating the username isn't enough; you'd better sign the entire database row and validate the signature before trying to use any of the data that's been returned. (And come up with some reason why you trust your own app code more than the database.)
The problem with such "silly assertions" is that they make you feel like you've added test coverage, when the thing you're testing is something like a database that is extensively tested by its vendor and by everyone else using the database, and there are other seams in your code which are much more likely to break. Meanwhile, they make the code longer and harder to read, which prevents readers of the code from easily identifying what those seams are.
(And by slowing down the API endpoint that talks to the database, it motivates other developers to try to put some caching in front of that endpoint, which may actually cause this sort of problem!)
I would not want to be that "human" atm
In 2011, I (in-house corp app dev) was still stuck with HTTP services (behind a firewall, accessible only via VPN).
In 2014, public facing mobile apps using HTTP was prevalent enough to prompt name and shame campaigns. [1] My fuzzy memory suggests some banks were still using HTTP.
[1] https://arstechnica.com/information-technology/2014/08/new-w...
However, showing the card issuer/bank + the final 4 or 5 digits of an account or card number is still extremely distressing. There are some services and vectors out there that can be engineered with just that information for sure.
Combine that with possibly exposed address, telephone number, and you are in very dangerous territory.
When I joined Klarna in 2011, the test was so easy that I joked I could score full marks on it even if I was hungover with no sleep. There was one question on the test that actually had 2 correct answers depending on what logic you applied. This was actually a real issue when recruiting, because there was a hard cut-off to make it into the engineering department, and several times I had to ask "what was their answer on question 12?"
It caused quite a bit of commotion at HR to change the official test scoring to 2 correct answers for that question.
Now the test is like a million times harder and your score at the end is between 0-10 and you have no idea how many questions you actually answered correctly. I would be very interested to know the "true" answers of these new tests to understand what kind of crazy logic you need to apply to get every question right. I'm almost certain it would take me longer to understand the answer than the time you have to do the test.
I did reply and explained my perspective clearly. Anymore than that will just not be constructive. From here on it will be just difference in opinion and no one will again anything.
And if you think I am troll then not feeding a troll is the best thing to do right?
Human error doesn't mean blame the human, it's better to look at the overall processes and system to figure out how to prevent human error the next time around.
One such thing is the abuse of layers and layers of abstractions. For example, many people (unfortunately, in my view) love to use ORMs and query builds, and things like these are much more easier to happen when things are too generic.
And signing the entire database row and validating it, and so on, might be unjustified for most people, especially if you already count with correction from a TLS layer, and you can just have the trade-off of adding a simple conditional to check if the data you receive is sane.
This is not something essential for everything, but that is nice to have, especially the further you're out of control.
For example, if you retrieve data from an external API you should not trust it blindly, but rely on your internal references (security concerns aside, I'm talking about other kind of erratic behavior or bad data).
So we generated our parser to fail if field ORG/1457 (made up) was not numeric max 8 digits. Or missing where mandatory.
Even if we never touched the data in that field.
Turns out that no-one else used the spec that way. No two were the same, so we had to basically implement two layers of parsing. One to put the data in a common parse tree, and the other to per-sending-mainframe interpret the data as how the sender had implemented.
We assumed that the mainframe would never send illformed data, and indeed that-could-never-happen. But they differed in what they thought was well formed.
When you test features like this or caching a response with a JWT it can be very easy to default to the happy path or ignore the impact of a large volume of concurrent users.
Those that care about the truth will be persuaded sufficiently by facts, and everyone outside of those that care about the truth I am not interested in spending any effort persuading.
> Boss - "Why do you think you are here, Jack?"
> JW - "I expect I am here so you can fire me"
> Boss - "I just spent a million dollars on your education - why would I fire you now?"
http://www.nickmilton.com/2016/03/jack-welch-on-learning-fro...
What was shifting at the time was developer views on using HTTPS for non-secure, unauthenticated portions of websites. This is where the "HTTPS Everywhere" plugin and other such movements came in.
The solution was to enter garbage for the first login since the "re-enter your password" page was served over https. I think they fixed it before 2011, but don't have an exact record of when.
And most of the time it's not even proper IQ-test but only Raven Matrice test + maybe quick math tests.
Funny thing was that I did very good (apparently according to the HR person) on one of them, but did horrible enough they didn't even call back on the second test.
grids my gear why this is still a common practice in Sweden. HR in Sweden seems to be about one or two decades behind rest of the world in their efficiency.
However, to the layperson, "bank details" definitely includes name of bank and last 4 digits of account number. It does come across as deceptive to use that terminology to respond to customer complaints.
[1] https://en.wikipedia.org/wiki/Minnesota_Multiphasic_Personal...
The thing is, I really needed that job... ended up going to another job that offered me a very low salary (I had no visa in the country , so was looking for a sponsor, which makes things a lot harder) and the company went bankrupt within a few months!
Anyway, I still got the visa, and then, with a few months to find another job with more peace of mind, I eventually got much nicer job, paying a lot more! But I still dread the though of doing an IQ test, despite my years of experience indicating I am more competent than average, at least.
The hiring company would send your answer sheet and work sheets off to the company to analyze and provide a score.
Anyone else remember those?
I don't think it's an authentication problem as there's no confirmed problem with proving an assertion as in e.g. (sha3("hello") === "0xabc") in the original post.
A lot of the web was still on http, including some banks.
Even Facebook was still primarliy http when Firesheep [1] came out in 2010.
Sorry to spoiler you but the answer is: no.
A moderator buried it for reasons explained here: https://news.ycombinator.com/item?id=27305371. Sorry for the delay, but these days you guys need to wait until I'm online to get explicit explanations, because I'm currently the only mod who's posting publicly.
(1) They're way too volatile.
(2) Even if they weren't, the popular cryptocurrencies today have fixed money supplies. A central bank cannot increase it to target moderate inflation.
I use them because consumer protections with other methods aren't as good here in the States. Paying with a credit card, if I have an issue with a vendor, after a good faith effort on my part to resolve the issue, I can just ask the credit card company to deal with it. (I don't abuse this, but I don't doubt there are people who do.)
There are better and worse credit card companies for this. American Express has great customer service but they aren't accepted in as many places.
We wouldn't have to ask if you had a public mod log (and banned sites list etc) and a public explanation of the algos that power HN.
Your comment reminds me of hotels - "X is available, just ask". A scheme clearly designed to reduce usage of X. I'm guessing the current audience is quite diverse, as most engineers would see through that kind of BS in about 0.2ms.
Crypto currencies are run by people as much as central banks are. People can have opinions and values. People forked of Ethereum into Ethereum Classic because they had an issue with the main chain's policy. ETC community is alive.
Building crypto currencies is all about optimizing for legitimacy [3]. We can build what we want, we just need to want it in the first place. No need to discount a whole field of computer science with a comment.
- 1: https://link.springer.com/article/10.1007/s11403-014-0127-3
- 2: https://github.com/reflexer-labs/whitepapers/blob/master/Eng...
A couple of years back, I was making https://lifeboxhq.com which involved users uploading quite a bit of content. I was happily testing security with some url resource enumeration and for some reason, I could non-deterministically access user uploads via url, even on accounts I didn't own. I spent several days looking at my Flask code, javascript, etc. to debug....
I knew it wasn't my code, but I was getting more and more frustrated, then I remembered I set up Cloudflare....
Remember to exclude certain routes from Cloudflare if you want to avoid arbitrary user content from being cached without authentication.
I lost so many great candidates that would be great hires to my teams at Klarna to that stupid test.
...and yes, you're being extremely hostile. There's a reason you got banned off of that other site...
While you may be literally true, the reality of this economic situation is full of far more gray area than you allow for.
If this confrontational, extrermist position is intended to try and wake people up to all this, I fear your message is outweighed by your snark.
And if you don't care about that, then I've wasted as much of my breath as you have yours.
Nope. That definitely wasn't an engineer.
Interesting for a country that slowly eradicates their indigenous people btw.
https://en.wikipedia.org/wiki/S%C3%A1mi_people#Discriminatio...
https://en.wikipedia.org/wiki/Swedification#Swedification_of...
Only afterwards I noticed on my bank statement. I sent them a gdpr request to delete my data.
There may not be an explicit "IQ" portion to the process, or a hard number, but they are absolutely filtering on intelligence. An uncomfortable aspect of our society that I'm both surprised and not surprised doesn't get talked about much.
My guess: each time a strand within the cable broke the cable stretched a little and the brake triggered.
Five years ago a company was hired to maintain the cable car. They took one look at the state of it, wrote to the operator (the town council) saying it needed to be shut down and exited the contract. It was an accident waiting to happen long before the brake fiasco.
> how banks can allow this
A court decided that blocking this "business model" would be anticompetitive.
https://news.ycombinator.com/item?id=23837866
https://news.ycombinator.com/item?id=23807944
https://news.ycombinator.com/item?id=23286685
https://news.ycombinator.com/item?id=23227833
https://news.ycombinator.com/item?id=23127622
https://news.ycombinator.com/item?id=22939878
https://news.ycombinator.com/item?id=22711604
https://news.ycombinator.com/item?id=22648990
https://news.ycombinator.com/item?id=22547697
Imagine creating such a log system in a company and expecting your colleagues to find such logs in such a manner. I'd move to get you fired.
Unfortunately, this often isn't the case of people who are worse off, not good at managing their finances, and often overwhelmed by bureaucracy.
They fall behind on payments, and then get taken to the cleaners on fees, deferred interest etc., often paying several times the actual price of the product. I've seen this happen (with different but similar services).
Less savvy people being sold stuff they can't afford on credit has been such a problem that some countries have made it illegal to extend credit to someone who can't afford it, which is obviously extremely hard to enforce.
This is hard to grasp for many here, because HN readers tend to be well above average intelligence. Try to think in terms of "imagine how dumb the average person is, and now realize half the people are dumber than that". Now add mental or physical health issues into the game.
The intention of all of those moderation comments, search links, etc., is to provide helpful information to people in specific contexts. Nobody's pretending that it's a global documentation system; no one's "cheating" or trying to fool anyone or trick people out of what is rightfully theirs. We're simply trying to answer people's questions and satisfy their curiosity while also staying focused on the overall purpose of the site.
Since people ask about specific examples all the time, and we always want to satisfy their curiosity, I post replies that go into detail about how we think about moderation, how what we did in any specific case relates to the guidelines, and ultimately how it all derives from the single thing we're trying to optimize HN for, which is curiosity (https://hn.algolia.com/?dateRange=all&page=0&prefix=true&sor...).
Over the years, those replies have grown into a body of explanations that add context to the site guidelines and the other brief things that have been 'officially' published about HN. That is analogous to how case law (the specific examples of how laws have been applied in the past) adds context to legal codes, which as you say can be inscrutable—they need examples to make sense. Another metaphor one could use for this is hermeneutics or midrash, but that has religious associations which would lead to distracting objections, so I don't go there. Yours is the first objection I remember anyone making to "case law"!
Of course this is not formal documentation, but it does contain all the explanation anyone could ask for—detailed answers to every conceivable question about HN moderation; just not in an easily discoverable form, as you say. That's why I'd like to compile this material into a more accessible format. We'd probably do that instead of making a public moderation log of every mod action—to come back to your original question—because it is more likely to help people understand what they're seeing. I've been waiting for the answers to converge into something that's worked-out enough to deserve publishing, but that has started to happen.
No one is expected to read that stuff, let alone find it for themselves; but I do include links to past explanations in current answers, so that anyone who wants to read more can click and get to them fairly easily. For example, here's such a link regarding the point I made in the previous paragraph: https://hn.algolia.com/?dateRange=all&page=0&prefix=true&que.... You'll notice that it contains the current comment, as well as 3 past ones on the same issue. It's an informal mechanism and it doesn't work perfectly (because the search links can also dig up extraneous stuff), but it's a lot better than nothing and has proven to be a good way to spread knowledge amongst the community—which is a hard problem btw.
I get why you might feel offended if we were telling you "just go dig up your answers in HN search"—that would be a little like customer support telling a user "look it up in the code, it's on Github". What we're actually telling you (and all users) is: if you have a question about how HN moderation works, just ask. If I see your question in the thread, I'll be happy to answer it—often at length, as I've done here—but we don't see everything in the threads, so it's better to email hn@ycombinator.com. The answer might end up including some links to past explanations, but you don't have to dig them up—we do that for you.
Although this mechanism is messy and insufficient, it has an interesting advantage: knowing that explanations can be reused in the future allows me to answer specific users' questions in much greater depth. If the only people reading this were you and the few others who ended up in this obscure corner of a thread while it was live, it wouldn't make sense to spend an hour writing an essay-length answer. But because the answer is helping to build a corpus of reusable explanations, the "economics" work: it's an investment in future readers in addition to current readers. Sometimes I take this to extremes, as with https://news.ycombinator.com/item?id=27162386 from a couple weeks ago—that was a lot of writing for answering a single user, even though we value single users. But it was also a big step in expanding the "corpus", making it worth doing.
It is a nice feedback loop: individual users benefit by getting richer explanations, the "case law" (can I use that term now?) benefits by getting a new detailed entry (a worked example, you could say), and the previous examples can be linked back to, making future explanations more meaningful.
This "system" emerged spontaneously over many years, in a bottom-up way very much in keeping with the exploratory, hackerish spirit that animates HN (at its best). That's what makes it so weird and esoteric, but also why it's alive and it works. Indeed, it's the only reason why any rich body of HN explanations exists at all. A top-down, bureaucratic approach would have led to "policies"—more the line of the manichean archenemy of the HN spirit. And anyway we'd never do that in the first place.
This approach has even changed how we moderate HN: it has evolved into a continuous, multi-sided dialogue (multilogue?) between the moderation subsystem and the community subsystem, that goes deeply into the why of things, tries to discover underlying principles and reflect them back to the community. For example, it led to "we're trying to optimize for just one thing", which I linked to above. This dialogue shapes the community in turn—it helps the forum regulate itself, even (I believe) when moderators aren't present.
The next step is to mine this material out of the subterranean thread-niches it's currently buried in, and to "scale" the economics by compiling it into more definitive forms that can be linked to and browsed. Perhaps it will look like an extended HN moderation FAQ or blog. That will be easier for new users to find and hopefully also save us a lot of time in the future, because as I said above, the answers have started to converge, which makes them more repetitive.
In all seriousness, better security. You are leaking whatever payload is sent right after VPN drops. An early version of the application had a defect because it did not check response payloads on an endpoint (the code handled errors, but 200 OK was all it needed on success). This is not what you want when the 200 OK is followed by the HTML of a hotel's wi-fi access page.
Cache invalidation is always a very tricky affair. It can work for a while but as complexity grows it gets very hard to maintain and debug. It's very much a "here be dragons" situation and you have to go into it with your guard up.
I was at a small startup that had a quick and dirty contractor built API. It worked, but for our largest customers, 99th percentile latency started going over the API gateway timeout. The quick and dirty hack on top of it was aggressive caching with too-clever invalidation logic. It worked until new features were added and then it started failing dramatically and unpredictably. The bugs were an absolute nightmare. We ended up spending almost a year cleaning up the data model, sharding things by customer, and fixing a bunch of N+1 queries, all so that we could get rid of our API cache layer and kill the bugs for good.
Manhandled in-house though...
Not sure why you were downvoted. I think your comment is rather fair. :) Although, let's give them some credit, they do have a pretty successful mixture of socialism and capitalism.
> Interesting for a country that slowly eradicates their indigenous people btw.
I think that sad story is over. They significantly ramped up protection for indigenous people.
However, if you make the assertion fail loud, then it provides an additional security layer and should be used as often as makes sense.
Used to, they’re broke now.
"We are truly sorry for any inconvenience..."
The conflict is imo not over, it is still going on. If it wasn't then Sweden couldn't produce 90% of all iron in Europe because the mine happens to be on Sami land.
I wrote recently about the different reasons why we do this, if anyone's interested: https://news.ycombinator.com/item?id=27132402.
I bet it's not as much as people railing against it would like to think.
I'm partly thinking of this because I fixed a (way less critical) bug today that boiled down to a (x - y) * z = 0 query that should've just been (x - y) = 0. But it was hidden by the whole expression being named, and that then seeming correct, it not being obvious that `z` could be 0 (or was involved at all) and as a result unwanted results would be included where x != y.
Probably the most obvious one is different IDs - have two fk columns that sound a bit similar and it's easy to come a cropper, getting 'random' records that correspond to a given ID but that's for the wrong table...
That's why I use GUID instead of integers. If you get a result, it was the right column.
> To use Klarna's pay later service, which defers payments for up to 30 days, shoppers only have to provide a name, email, date of birth, mobile number and billing address.
It’s mind blowing that’s all the information you need to process a payment via Klarna.
There is a strong correlation between IQ and professional achievement whether you want to believe it or not.
Edit: Found an article in German - https://www.sueddeutsche.de/geld/zahlung-per-sofortueberweis...
They claim they need to do this to make sure there is sufficient money in the account, even with transactions that might not be reflected in the balance, and they also check for other "Sofortüberweisungen" to detect fraud. Makes sense in a way but still quite shady. If there wasn't enough money in my account, or other transfers pending would my bank even allow their transfer?
This is the lie of "identity theft". It's not identity theft, it's money/goods fraud, from a bank that didn't do proper authentication.
Aren't they?
> it wold only have to happen a few times before they realize it's not worth it
That's an assumption. Someone did some A/B testing and said this payment flow results in X% increased sales, resulting in Y% more revenue for Klarna, it results in Z% more fraud. I don't even object to this per-se.
If Y is greater than Z, they will do it.
If they are especially awful they will consider that of the Z% of fraud it will result in A% still being paid for and B% being recovered in debt collection. That is awful.
"A somewhat tongue-in-cheek but surprisingly useful maxim of high finance is that it is good for your career if you lose a billion dollars. I mean, if you lose a billion dollars for your employer you will probably be fired, though that depends on who your employer is and how much money you started with and what you did to lose it. But lots of other employers will be excited to hire you, once they learn that you lost a billion dollars for someone else."
https://www.bloomberg.com/opinion/articles/2021-05-26/exxon-...
You could ask "what was the fallout?", "Did the client get compensated?", or "did you make procedural changes afterwards?" without being as confrontational.
Less people will post about their mistakes if they know they're going to be lambasted for them. We can learn from these mistakes if they're shared or they can be a timely reminder of stakes if we're slipping into complacency. So we probably don't want to discourage such posts (especially since it's rarer for people to want to talk about failures that successes).
Whether they are likely to have a competent security team with sufficient budget is an exercise left to the reader.
My interactions with Klarna have so far failed to inspire similar confidence.
These gigantic government IT projects are also a good way to funnel taxpayer money to the right pockets, that's why they're always behind schedule and over budget (just like all government physical infrastructure projects) and if you look closely it's always the same 2-3 companies getting all the contracts.
In Sweden, the classic "order by post" required paying at the post office as you picked your parcel up, with only the pick-up slip (with the total to pay) being delivered to the address.
I have seen a few Swedish companies who didn't use the Swedish postal order system, instead opting to send a package with a giro slip and an "pay within X days" inside.
My understanding is that the post office took a small cut of the postal order payment, as a fee for guaranteeing payment. And the companies instead sending a giro slip had enough compliance with paying that it netted more money.
Not always. Like if you initialize middleware by using a "lambda" (closure), and you from within that closure creates a new closure.
It means that you need to be aware of the context the outer closure is used in. If it is only instantiated once during initialization, it's free variables are in essence "hidden" global variables. Not easy to spot.
The problem is that the law in Finland is written so that even if the collection is baseless the supposed debtor needs to actively manage it or end up in legal jeopardy. Which is rather unfair if you are a victim of identity theft.
“Also, the United Nations Committee against Torture condemned Sweden for having violated the principle of non refoulement provided in Article 3 of the Convention against Torture.”
https://www.cairn.info/revue-internationale-de-droit-penal-2...
I am not sure how this is even legal under the PSD2 in EU. It might not be. But Klarna does not seem to care, and I really hope someone will take them to court over this.
After 3 support calls and several emails, we just gave up. Fortunately it was just €12.
This was so frustrating that we now avoid paying with Klarna whenever possible.
https://www.ceicdata.com/en/indicator/sweden/foreign-exchang...
https://en.wikipedia.org/wiki/Payment_Services_Directive#Rev...
They would probably not measure fraud but just losses directly.
(No knowledge of the details, just speculation based on the discussion here)
Such is the cloud software... :) Cloud, besides APIs, i.e managing hardware at scale was not really what they did.
They did roll 1000s of vms per week through it in ci/cd flows though.
As such it did what it was supposed to do - docker/containers was not a thing at that point in time, and I remember thinking it was pretty awesome.
To many nifty engineers, with long fingers, for their own good though. You need to be strict with automations if you want to keep something like that running reliably over time.
First, if you're just hiring assistants from the Philippines they could just have someone else take the test or get around it some other way.
Second, you have no good data to support this hiring practice. You're free to use it, but it's no better than just hiring a random person from your pool of applicants. You might as well screen based on their favorite color too to just make up filtering criteria.