Active / Trash - Whose responsibility is it? (1 Viewer)

jwcolby54

Member
Local time
Today, 12:49
Joined
May 19, 2025
Messages
208
I use classes to generalize activities in the user interface. The objective is to standardize the interface across forms. For example every form can have an active / trash capability without having to do that in every form's code-behind-form class.

One example from my past, I used a pair of boolean fields called Active and Trash. I placed them in the vast majority of my tables. When a new record is created Active was set true and Trash is set false.

I created a class to handle this. It wrapped a pair of check boxes bound to these fields, chkActive and chkTrash. It also accepted a reference to the form so that I could sink the form's BeforeDeleteConfirm. This allows me to cancel the delete, set the trash flag and clear the active flag. The class also allows me to set the visibility of these controls true or false, thus hiding the control under most circumstances, but allowing them to be visible for a supervisor to recover deleted records.

This is a great class to earn pizza from the user.

"Sir, I am desperate. I just deleted a record i shouldn't have"
"Order a pizza and sit down, I'll fix it"

The dev asks a few questions, finds the record, which hasn't really been deleted. Brings it back to life.
The user leaves, so very grateful. Not realizing that the pizza will be delivered in a couple of moments...:D

Works every time!

Your thoughts?
 
First, I applaud your ability to get pizza. Wish I could still eat it, but the oily cheeses and most meat toppings screw with my liver.

Second, on a more serious note, if both "Active" and "Trash" are visible as CHECK boxes (not as a radio button), that implies that, unless you do some behind-the-scenes code on the check boxes' Click or Change events, it might be possible to have both checked or both unchecked. This leads to questions of "is that all there is - or do you have hidden code behind them?" and "what would it mean if both check boxes were in the same state, true OR false?"
 
I had such a flag on one of my dbs, but just Active. If not active, it was not picked up for the db. So one field indicated both states?

Bit like having a date in an Unactive field. If populated with date it tells you they are unactive, but also when they went inactive?
 
In our case :
  • Any thing that is not active, is trash. So why you need 2 where 1 can do the same. We have 1 long text field (why), an integer field (who), a datetime field (when) for deleted records.
  • Supervisors don't want to see the deleted records all over the place. Every search form has an option to include deleted records in the result. If selected, deleted records would be shown. This option is set to off as default.
  • Why you should try to hide a deleted record from normal users? If a record is deleted, everyone should see it, and check why/when/who deleted it.
    Imagine an order was deleted by A, but two days later B searches for the order. If it's not there, he thinks the order was never received. But being able to view it, he can see why/when/who deleted the order.
  • our supervisor don't like pizza. So anyone who deleted a record, can bring it back to life. Beforeupdate event of the form checks to see if the user is admin or is the person who deleted the record. Only admins or the one who deleted a record can retrieve it. Others only can view it.
 
Last edited:
First, I applaud your ability to get pizza. Wish I could still eat it, but the oily cheeses and most meat toppings screw with my liver.

Second, on a more serious note, if both "Active" and "Trash" are visible as CHECK boxes (not as a radio button), that implies that, unless you do some behind-the-scenes code on the check boxes' Click or Change events, it might be possible to have both checked or both unchecked. This leads to questions of "is that all there is - or do you have hidden code behind them?" and "what would it mean if both check boxes were in the same state, true OR false?"
Active and trash are independent. A record can be activeor inactive. Think a client. They haven't ordered anything in a year and the company poilcy is that if a client hasn't ordered by X they are inactive. But the client isn't trash. They are not going to be deleted. Probably ever.

OTOH records can be "deleted". Let's use a different object. A car was leased. It is active. It is not trash. We enter it in the database. We get ready to assign it to the boss but it won't start. The delivery guy raced it on the way over and blew the engine. There is absolutely no reason to keep it in the database cause we just returned it to the leasing company. So we "delete it". We set the trash flag. Obviously it is no longer active either so we set the Active flag false as well.

Independent concepts, independent flags but related in implementation. So the class will wrap both check boxes (not radio buttons). And the class will implement a set of rules for deletion, and allow the user to determine what happens on undelete.
 
In our case :
  • Any thing that is not active, is trash. So why you need 2 where 1 can do the same. We have 1 long text field (why), an integer field (who), a datetime field (when) for deleted records.
  • Supervisors don't want to see the deleted records all over the place. Every search form has an option to include deleted records in the result. If selected, deleted records would be shown. This option is set to off as default.
  • Why you should try to hide a deleted record from normal users? If a record is deleted, everyone should see it, and check why/when/who deleted it.
    Imagine an order was deleted by A, but two days later B searches for the order. If it's not there, he thinks the order was never received. But being able to view it, he can see why/when/who deleted the order.
  • our supervisor don't like pizza. So anyone who deleted a record, can bring it back to life. Beforeupdate event of the form checks to see if the user is admin or is the person who deleted the record. Only admins or the one who deleted a record can retrieve it. Others only can view it.
I never said anything not active is trash. A client can be inactive but we need to keep their stuff around. NOT trash!
 
In our case :
  • Any thing that is not active, is trash. So why you need 2 where 1 can do the same. We have 1 long text field (why), an integer field (who), a datetime field (when) for deleted records.
  • Supervisors don't want to see the deleted records all over the place. Every search form has an option to include deleted records in the result. If selected, deleted records would be shown. This option is set to off as default.
  • Why you should try to hide a deleted record from normal users? If a record is deleted, everyone should see it, and check why/when/who deleted it.
    Imagine an order was deleted by A, but two days later B searches for the order. If it's not there, he thinks the order was never received. But being able to view it, he can see why/when/who deleted the order.
  • our supervisor don't like pizza. So anyone who deleted a record, can bring it back to life. Beforeupdate event of the form checks to see if the user is admin or is the person who deleted the record. Only admins or the one who deleted a record can retrieve it. Others only can view it.
  • Any thing that is not active, is trash. So why you need 2 where 1 can do the same. We have 1 long text field (why), an integer field (who), a datetime field (when) for deleted records.
Not true as explained
  • Supervisors don't want to see the deleted records all over the place. Every search form has an option to include deleted records in the result. If selected, deleted records would be shown. This option is set to off as default.
This is a business decision. In my client's case a supervisor's job is to supervise. That may include recovering records accidentally deleted. It may include actually deleting records that really should be deleted.
  • Why you should try to hide a deleted record from normal users? If a record is deleted, everyone should see it, and check why/when/who deleted it.
    Imagine an order was deleted by A, but two days later B searches for the order. If it's not there, he thinks the order was never received. But being able to view it, he can see why/when/who deleted the order.
This is also a business decision. "There are more ways to kill a cat than choking it to death on butter" as my southern born mamma used to say.

The quick answer is that perhaps you want to DISPLAY trash records but only allow supervisors to recover the records? The point really is that the class implements these rules. In general, it should not be different rules implemented by each and every form you design.
  • our supervisor don't like pizza. So anyone who deleted a record, can bring it back to life. Beforeupdate event of the form checks to see if the user is admin or is the person who deleted the record. Only admins or the one who deleted a record can retrieve it. Others only can view it.
Yes but can anyone who sees ANY deleted record bring ANY deleted record back to life? What if it really should be deleted? What if it was deleted by mistake? How does a user who did not delete a record know whether it really is trash? Should any user be able to REALLY delete a client? If they accidentally delete it, it can always be gotten back because it is just a flag but the general user has no business undeleting things that they did not delete.

  • Only admins or the one who deleted a record can retrieve it. Others only can view it.
Great, so implement that in the class which handles the delete flag.

Now you are getting into what I call Presentation level security. checking who a user is, what role they play, who is allowed to do what... But the Active/trash class can certainly call out to the security stuff and ask the question "who is the user logged in and what are they allowed to do"

I cannot get into that side of things and keep stuff simple enough to teach concepts.
 
I may be wrong, but somehow I feel my reply offended you and you took my response as something that I didn't mean it to be. You ended your post with "Your thoughts?", and I explained (or tried to explain) how we do it and why it's different with your method.


I already have explained all your questions in my post(#4). The only thing that I didn't explain is: (If I understand your question correctly)

How does a user who did not delete a record know whether it really is trash?
When a user searches for a record, and the record is marked as deleted by another user, s/he receives a message
"Nothing found."
and a small red text at the bottom says:
"xxx deleted record(s) for the submitted search keywords were found. Click here to view it"

If the submitted search keywords returns several records, a small textbox at the bottom of the result says : "And xxx more deleted record. Click here to include deleted items too."
(xxx being the number of found deleted records)
 
Last edited:
That is fine. Some fo
I think 99% of folks reading this thread thought that was what you meant (not active = trash)! :ROFLMAO:

I would use date fields instead of Booleans.

Null = active or not trash
Date shows when state was changed
Some folks want to record who did the delete. Whatever works for you and your client. For me and my clients a simple "it has been done" works. I can see recording the date that a client was marked inactive. That makes sense and is usable data. When a record was deleted.... IMHO doesn't tell me enough to make it worth while.

What I am trying to teach is why we use classes at all. The answer is encapsulation of code and information to solve a problem. So whether you choose to use a date is entirely irrelevant to the why we use classes.

OTOH I absolutely do want this discussion to include "we do it this way because". We can select the manner that makes the most sense and then we as a group can implement a class which processes the data and the rules correctly.

Just know that whatever I work on in this regard will end up in my book. And likely on my blog as well.
 
Last edited:
Let's discuss for a minute date vs boolean. Once we get into "when it was done, in my mind that information has to be worth the effort to deal with it. For example for the active flag, knowing when a client was set inactive might be useful. Why / how would it be useful?

Knowing when a record was set to trash? IMHO this is less obvious why it is useful. Why would it be useful?

This a conversation usually had with the client.
 
This is what I do too, use date fields, and I record the UserID of whoever did the delete. I mean, not always, but if it matters.
The whole "who done it" is also a whole nuther discussion. Are we implementing an audit trail as well? Certainly not in this class specifically I would think. I would really love to implement an audit trail but it gets real deep real quick.

My feeling is that if something is happening that shouldn't be happening, usually we want to educate all the users to "not do that", or... implement a method of preventing the user from doing that thing. Pointing fingers is (IMO) usually counter productive.
 
One thing that I tried to stress with my clients is that collecting every piece of data in the world doesn't work. Anything you decide to collect needs to be reliably and religiously entered or... it ends up being a detriment rather than a benefit. Ever run into data missing in reports? Yea that!

The nice thing about using a class to implement whatever the rules end up being... is that it is automatic and doesn't require (much) user input.
 
Say I wanted to know the number of orders I have outstanding today, I could write a query:
SQL:
SELECT
  Format(OrderDate, 'yyyy\-mm') AS Period,
  COUNT(*) AS Outstanding
FROM orders
WHERE DateCompleted IS NULL
  AND DateDeleted IS NOT NULL
GROUP BY
  Format(OrderDate, 'yyyy\-mm')
;

But say I wanted to see what my outstanding orders looked like last week, and I had an order which came in three weeks ago, but was deleted yesterday, I can use:
SQL:
SELECT
  Format(OrderDate, 'yyyy\-mm') AS Period,
  COUNT(*) AS Outstanding
FROM orders
WHERE OrderDate <= DateAdd('w', -1, Date),
  AND DateCompleted IS NULL
  AND (DateDeleted IS NOT NULL OR DateDeleted > DateAdd('w', -1, Date)
GROUP BY
  Format(OrderDate, 'yyyy\-mm')
;

This gives the ability to view data as slices in time.
 
Say I wanted to know the number of orders I have outstanding today, I could write a query:
SQL:
SELECT
  Format(OrderDate, 'yyyy\-mm') AS Period,
  COUNT(*) AS Outstanding
FROM orders
WHERE DateCompleted IS NULL
  AND DateDeleted IS NOT NULL
GROUP BY
  Format(OrderDate, 'yyyy\-mm')
;

But say I wanted to see what my outstanding orders looked like last week, and I had an order which came in three weeks ago, but was deleted yesterday, I can use:
SQL:
SELECT
  Format(OrderDate, 'yyyy\-mm') AS Period,
  COUNT(*) AS Outstanding
FROM orders
WHERE OrderDate <= DateAdd('w', -1, Date),
  AND DateCompleted IS NULL
  AND (DateDeleted IS NOT NULL OR DateDeleted > DateAdd('w', -1, Date)
GROUP BY
  Format(OrderDate, 'yyyy\-mm')
;

This gives the ability to view data as slices in time.
Ok, understood. Except that deleting orders? Are you immediately archiving your orders or something? Why is the order being deleted? In any event, if you need to know when, then you need to know when. Business rules are not my domain, implementing business rules is my domain.
 
Discussing active & trash flags... I had something not dissimilar when working with the U.S. Navy which, in their infinite wisdom, said that we could not archive & delete a record from the main table until the last (implied) step in the process had been complete for 6 months. I.e. the project manager could see the status history of things for another half-year after all we handled.

The process I was tracking could have multiple steps and often they were "on hold" waiting for external resolution, so as you can guess, some records hung around a LOT longer than others. I had a status code that showed the most recent status of the action being recorded and the date on which that occurred. Of the statuses I kept, about 25% of them implied "no further action required." The status codes broke out into three main groups - active (scheduled), waiting, or done (which didn't always mean completed, but DID mean nothing else was expected.)

I could have done the archiving with pure logic, but the Navy wanted a more hands-on approach. So I had a Y/N flag that said "Eligible to archive" and it got set when I ran the query to find the dormant, closed records. I had a report to be run listing the eligible records, along with enough other info in the query to allow verification. FINALLY, once I had all the other tests and checks completed, I could run the query that, in two parts, transferred the eligible records to a secondary storage table and then deleted the record from the primary table.
 
implementing business rules is my domain.
But the implementation cost, if you flag trash with a boolean vs a date, is the same. The effort required in all cases: 1) add a field to a table, 2) handle a UI event and save a trash value flag, 3) filter future queries based the trash value flag.

In a landscape where storage space is effectively free (because a date takes more space), the cost of implementing this pattern is fixed. The data type of the flag is irrelevant. The advantage of a date is--for the same implementation cost--you get a time dimension free of charge.

So if just the burger costs $5, but the burger & fries also costs $5, it's tough to sell the solo burger as a value advantage.
 

Users who are viewing this thread

Back
Top Bottom