It certainly helps to minimize the time between querying the last value and saving a new record.
You already found that sorting in descending order is more efficient. The next thing to do is only query the Id value, not the entire entity:
container.HourlyHealthEntries
.Where(h => h.Date == healthEntry.Date)
.Where(h => h.StoreGuid == healthEntry.StoreGuid)
.Select(h => h.RowIndex)
.OrderByDescending(i => i)
.FirstOrDefault();
Now a minimum amount of data crosses the wire and only an integer is created client-side.
Now immediately use this value to set the PK value, and save.
Enclose this in a TransactionScope
with isolationlevel serializable:
var opt = new TransactionOptions();
opt.IsolationLevel = System.Transactions.IsolationLevel.Serializable;
using(var ts = new TransactionScope(TransactionScopeOption.Required, opt))
{
...
Now you're only getting conflicts when other users try to modify the records you read in the transaction, but they can still read them.